├── .gitignore ├── .idea ├── .gitignore ├── .name ├── compiler.xml ├── gradle.xml ├── inspectionProfiles │ └── Project_Default.xml ├── misc.xml ├── other.xml └── vcs.xml ├── LICENSE ├── README.md ├── VelocityX ├── .gitignore ├── build.gradle ├── consumer-rules.pro ├── proguard-rules.pro └── src │ ├── androidTest │ └── java │ │ └── dev │ │ └── codepur │ │ └── velocityx │ │ ├── ExampleInstrumentedTest.kt │ │ ├── Theme.kt │ │ └── VxTextTest.kt │ ├── main │ ├── AndroidManifest.xml │ └── java │ │ └── dev │ │ └── codepur │ │ └── velocityx │ │ ├── Vx.kt │ │ ├── VxWidgetBuilder.kt │ │ ├── compose │ │ ├── VxBox.kt │ │ ├── VxCard.kt │ │ ├── VxColumn.kt │ │ ├── VxImage.kt │ │ ├── VxRow.kt │ │ ├── VxSpacer.kt │ │ ├── VxText.kt │ │ └── VxWidgets.kt │ │ ├── extensions │ │ ├── Language.kt │ │ └── date_time_ext.kt │ │ └── mixin │ │ ├── VxAlignmentMixin.kt │ │ ├── VxColorMixin.kt │ │ ├── VxGradientMixin.kt │ │ ├── VxModifierMixin.kt │ │ ├── VxPaddingMixin.kt │ │ ├── VxRowColumnAlignment.kt │ │ ├── VxSizeMixin.kt │ │ └── VxTransformMixin.kt │ └── test │ └── java │ └── dev │ └── codepur │ └── velocityx │ └── ExampleUnitTest.kt ├── app ├── .gitignore ├── build.gradle ├── proguard-rules.pro └── src │ ├── androidTest │ └── java │ │ └── com │ │ └── example │ │ └── velocityXAndroid │ │ └── ExampleInstrumentedTest.kt │ ├── main │ ├── AndroidManifest.xml │ ├── java │ │ └── com │ │ │ └── example │ │ │ └── velocityXAndroid │ │ │ ├── MainActivity.kt │ │ │ └── ui │ │ │ └── theme │ │ │ ├── Color.kt │ │ │ ├── Theme.kt │ │ │ └── Type.kt │ └── res │ │ ├── drawable-v24 │ │ ├── flpy.png │ │ └── ic_launcher_foreground.xml │ │ ├── drawable │ │ └── ic_launcher_background.xml │ │ ├── mipmap-anydpi-v26 │ │ ├── ic_launcher.xml │ │ └── ic_launcher_round.xml │ │ ├── mipmap-hdpi │ │ ├── ic_launcher.webp │ │ └── ic_launcher_round.webp │ │ ├── mipmap-mdpi │ │ ├── ic_launcher.webp │ │ └── ic_launcher_round.webp │ │ ├── mipmap-xhdpi │ │ ├── ic_launcher.webp │ │ └── ic_launcher_round.webp │ │ ├── mipmap-xxhdpi │ │ ├── ic_launcher.webp │ │ └── ic_launcher_round.webp │ │ ├── mipmap-xxxhdpi │ │ ├── ic_launcher.webp │ │ └── ic_launcher_round.webp │ │ ├── values │ │ ├── colors.xml │ │ ├── strings.xml │ │ └── themes.xml │ │ └── xml │ │ ├── backup_rules.xml │ │ └── data_extraction_rules.xml │ └── test │ └── java │ └── com │ └── example │ └── velocityXAndroid │ └── ExampleUnitTest.kt ├── build.gradle ├── gradle.properties ├── gradle └── wrapper │ ├── gradle-wrapper.jar │ └── gradle-wrapper.properties ├── gradlew ├── gradlew.bat └── settings.gradle /.gitignore: -------------------------------------------------------------------------------- 1 | *.iml 2 | .gradle 3 | /local.properties 4 | /.idea/caches 5 | /.idea/libraries 6 | /.idea/modules.xml 7 | /.idea/workspace.xml 8 | /.idea/navEditor.xml 9 | /.idea/assetWizardSettings.xml 10 | .DS_Store 11 | /build 12 | /captures 13 | .externalNativeBuild 14 | .cxx 15 | local.properties 16 | -------------------------------------------------------------------------------- /.idea/.gitignore: -------------------------------------------------------------------------------- 1 | # Default ignored files 2 | /shelf/ 3 | /workspace.xml 4 | -------------------------------------------------------------------------------- /.idea/.name: -------------------------------------------------------------------------------- 1 | VelocityXExample -------------------------------------------------------------------------------- /.idea/compiler.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | -------------------------------------------------------------------------------- /.idea/gradle.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 19 | 20 | -------------------------------------------------------------------------------- /.idea/inspectionProfiles/Project_Default.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 23 | -------------------------------------------------------------------------------- /.idea/misc.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 10 | 11 | 12 | 13 | 14 | 15 | 17 | -------------------------------------------------------------------------------- /.idea/other.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 6 | -------------------------------------------------------------------------------- /.idea/vcs.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | Apache License 2 | Version 2.0, January 2004 3 | http://www.apache.org/licenses/ 4 | 5 | TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION 6 | 7 | 1. Definitions. 8 | 9 | "License" shall mean the terms and conditions for use, reproduction, 10 | and distribution as defined by Sections 1 through 9 of this document. 11 | 12 | "Licensor" shall mean the copyright owner or entity authorized by 13 | the copyright owner that is granting the License. 14 | 15 | "Legal Entity" shall mean the union of the acting entity and all 16 | other entities that control, are controlled by, or are under common 17 | control with that entity. For the purposes of this definition, 18 | "control" means (i) the power, direct or indirect, to cause the 19 | direction or management of such entity, whether by contract or 20 | otherwise, or (ii) ownership of fifty percent (50%) or more of the 21 | outstanding shares, or (iii) beneficial ownership of such entity. 22 | 23 | "You" (or "Your") shall mean an individual or Legal Entity 24 | exercising permissions granted by this License. 25 | 26 | "Source" form shall mean the preferred form for making modifications, 27 | including but not limited to software source code, documentation 28 | source, and configuration files. 29 | 30 | "Object" form shall mean any form resulting from mechanical 31 | transformation or translation of a Source form, including but 32 | not limited to compiled object code, generated documentation, 33 | and conversions to other media types. 34 | 35 | "Work" shall mean the work of authorship, whether in Source or 36 | Object form, made available under the License, as indicated by a 37 | copyright notice that is included in or attached to the work 38 | (an example is provided in the Appendix below). 39 | 40 | "Derivative Works" shall mean any work, whether in Source or Object 41 | form, that is based on (or derived from) the Work and for which the 42 | editorial revisions, annotations, elaborations, or other modifications 43 | represent, as a whole, an original work of authorship. For the purposes 44 | of this License, Derivative Works shall not include works that remain 45 | separable from, or merely link (or bind by name) to the interfaces of, 46 | the Work and Derivative Works thereof. 47 | 48 | "Contribution" shall mean any work of authorship, including 49 | the original version of the Work and any modifications or additions 50 | to that Work or Derivative Works thereof, that is intentionally 51 | submitted to Licensor for inclusion in the Work by the copyright owner 52 | or by an individual or Legal Entity authorized to submit on behalf of 53 | the copyright owner. For the purposes of this definition, "submitted" 54 | means any form of electronic, verbal, or written communication sent 55 | to the Licensor or its representatives, including but not limited to 56 | communication on electronic mailing lists, source code control systems, 57 | and issue tracking systems that are managed by, or on behalf of, the 58 | Licensor for the purpose of discussing and improving the Work, but 59 | excluding communication that is conspicuously marked or otherwise 60 | designated in writing by the copyright owner as "Not a Contribution." 61 | 62 | "Contributor" shall mean Licensor and any individual or Legal Entity 63 | on behalf of whom a Contribution has been received by Licensor and 64 | subsequently incorporated within the Work. 65 | 66 | 2. Grant of Copyright License. Subject to the terms and conditions of 67 | this License, each Contributor hereby grants to You a perpetual, 68 | worldwide, non-exclusive, no-charge, royalty-free, irrevocable 69 | copyright license to reproduce, prepare Derivative Works of, 70 | publicly display, publicly perform, sublicense, and distribute the 71 | Work and such Derivative Works in Source or Object form. 72 | 73 | 3. Grant of Patent License. Subject to the terms and conditions of 74 | this License, each Contributor hereby grants to You a perpetual, 75 | worldwide, non-exclusive, no-charge, royalty-free, irrevocable 76 | (except as stated in this section) patent license to make, have made, 77 | use, offer to sell, sell, import, and otherwise transfer the Work, 78 | where such license applies only to those patent claims licensable 79 | by such Contributor that are necessarily infringed by their 80 | Contribution(s) alone or by combination of their Contribution(s) 81 | with the Work to which such Contribution(s) was submitted. If You 82 | institute patent litigation against any entity (including a 83 | cross-claim or counterclaim in a lawsuit) alleging that the Work 84 | or a Contribution incorporated within the Work constitutes direct 85 | or contributory patent infringement, then any patent licenses 86 | granted to You under this License for that Work shall terminate 87 | as of the date such litigation is filed. 88 | 89 | 4. Redistribution. You may reproduce and distribute copies of the 90 | Work or Derivative Works thereof in any medium, with or without 91 | modifications, and in Source or Object form, provided that You 92 | meet the following conditions: 93 | 94 | (a) You must give any other recipients of the Work or 95 | Derivative Works a copy of this License; and 96 | 97 | (b) You must cause any modified files to carry prominent notices 98 | stating that You changed the files; and 99 | 100 | (c) You must retain, in the Source form of any Derivative Works 101 | that You distribute, all copyright, patent, trademark, and 102 | attribution notices from the Source form of the Work, 103 | excluding those notices that do not pertain to any part of 104 | the Derivative Works; and 105 | 106 | (d) If the Work includes a "NOTICE" text file as part of its 107 | distribution, then any Derivative Works that You distribute must 108 | include a readable copy of the attribution notices contained 109 | within such NOTICE file, excluding those notices that do not 110 | pertain to any part of the Derivative Works, in at least one 111 | of the following places: within a NOTICE text file distributed 112 | as part of the Derivative Works; within the Source form or 113 | documentation, if provided along with the Derivative Works; or, 114 | within a display generated by the Derivative Works, if and 115 | wherever such third-party notices normally appear. The contents 116 | of the NOTICE file are for informational purposes only and 117 | do not modify the License. You may add Your own attribution 118 | notices within Derivative Works that You distribute, alongside 119 | or as an addendum to the NOTICE text from the Work, provided 120 | that such additional attribution notices cannot be construed 121 | as modifying the License. 122 | 123 | You may add Your own copyright statement to Your modifications and 124 | may provide additional or different license terms and conditions 125 | for use, reproduction, or distribution of Your modifications, or 126 | for any such Derivative Works as a whole, provided Your use, 127 | reproduction, and distribution of the Work otherwise complies with 128 | the conditions stated in this License. 129 | 130 | 5. Submission of Contributions. Unless You explicitly state otherwise, 131 | any Contribution intentionally submitted for inclusion in the Work 132 | by You to the Licensor shall be under the terms and conditions of 133 | this License, without any additional terms or conditions. 134 | Notwithstanding the above, nothing herein shall supersede or modify 135 | the terms of any separate license agreement you may have executed 136 | with Licensor regarding such Contributions. 137 | 138 | 6. Trademarks. This License does not grant permission to use the trade 139 | names, trademarks, service marks, or product names of the Licensor, 140 | except as required for reasonable and customary use in describing the 141 | origin of the Work and reproducing the content of the NOTICE file. 142 | 143 | 7. Disclaimer of Warranty. Unless required by applicable law or 144 | agreed to in writing, Licensor provides the Work (and each 145 | Contributor provides its Contributions) on an "AS IS" BASIS, 146 | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or 147 | implied, including, without limitation, any warranties or conditions 148 | of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A 149 | PARTICULAR PURPOSE. You are solely responsible for determining the 150 | appropriateness of using or redistributing the Work and assume any 151 | risks associated with Your exercise of permissions under this License. 152 | 153 | 8. Limitation of Liability. In no event and under no legal theory, 154 | whether in tort (including negligence), contract, or otherwise, 155 | unless required by applicable law (such as deliberate and grossly 156 | negligent acts) or agreed to in writing, shall any Contributor be 157 | liable to You for damages, including any direct, indirect, special, 158 | incidental, or consequential damages of any character arising as a 159 | result of this License or out of the use or inability to use the 160 | Work (including but not limited to damages for loss of goodwill, 161 | work stoppage, computer failure or malfunction, or any and all 162 | other commercial damages or losses), even if such Contributor 163 | has been advised of the possibility of such damages. 164 | 165 | 9. Accepting Warranty or Additional Liability. While redistributing 166 | the Work or Derivative Works thereof, You may choose to offer, 167 | and charge a fee for, acceptance of support, warranty, indemnity, 168 | or other liability obligations and/or rights consistent with this 169 | License. However, in accepting such obligations, You may act only 170 | on Your own behalf and on Your sole responsibility, not on behalf 171 | of any other Contributor, and only if You agree to indemnify, 172 | defend, and hold each Contributor harmless for any liability 173 | incurred by, or claims asserted against, such Contributor by reason 174 | of your accepting any such warranty or additional liability. 175 | 176 | END OF TERMS AND CONDITIONS 177 | 178 | APPENDIX: How to apply the Apache License to your work. 179 | 180 | To apply the Apache License to your work, attach the following 181 | boilerplate notice, with the fields enclosed by brackets "[]" 182 | replaced with your own identifying information. (Don't include 183 | the brackets!) The text should be enclosed in the appropriate 184 | comment syntax for the file format. We also recommend that a 185 | file or class name and description of purpose be included on the 186 | same "printed page" as the copyright notice for easier 187 | identification within third-party archives. 188 | 189 | Copyright [yyyy] [name of copyright owner] 190 | 191 | Licensed under the Apache License, Version 2.0 (the "License"); 192 | you may not use this file except in compliance with the License. 193 | You may obtain a copy of the License at 194 | 195 | http://www.apache.org/licenses/LICENSE-2.0 196 | 197 | Unless required by applicable law or agreed to in writing, software 198 | distributed under the License is distributed on an "AS IS" BASIS, 199 | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 200 | See the License for the specific language governing permissions and 201 | limitations under the License. 202 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # VelocityX 2 | 3 |

4 | 5 | VelocityX 6 | 7 |

8 | VelocityX - A minimalist framework | Product Hunt 9 | 10 | [![VelocityX](https://img.shields.io/badge/velocityx-fast-red?style=for-the-badge)](https://github.com/iampawan/VelocityXAndroidCompose) 11 | 12 | [![GitHub Release Date](https://img.shields.io/github/release-date/iampawan/velocityXandroidcompose.svg?style=for-the-badge)](https://github.com/iampawan/VelocityXAndroidCompose) 13 | [![GitHub issues](https://img.shields.io/github/issues/iampawan/VelocityXAndroidCompose.svg?style=for-the-badge)](https://github.com/iampawan/VelocityXAndroidCompose/issues) 14 | [![GitHub top language](https://img.shields.io/github/languages/top/iampawan/VelocityXAndroidCompose.svg?style=for-the-badge)](https://github.com/iampawan/VelocityXAndroidCompose) 15 | 16 | Discord 17 | 18 | ### Show some :heart: and star the repo. 19 | 20 | [![GitHub followers](https://img.shields.io/github/followers/iampawan.svg?style=social&label=Follow)](https://github.com/iampawan/) 21 | [![Twitter Follow](https://img.shields.io/twitter/follow/imthepk.svg?style=social)](https://twitter.com/imthepk) 22 | 23 | [![Open Source Love](https://badges.frapsoft.com/os/v1/open-source.svg?v=102)](https://opensource.org/licenses/Apache-2.0) 24 | 25 | --- 26 | 27 | ## [Subscribe to Codepur](https://codepur.dev/) 28 | 29 | --- 30 | 31 | [**VelocityX**](https://velocityx.dev/) is a 100% free Jetpack open-source minimalist UI Framework built with Kotlin & Jetpack Compose to make Android development easier and more joyful than ever. 32 | 33 | ## Inspired from Tailwindcss and Flutter 34 | 35 | ```kotlin 36 | "Welcome to VelocityX".text.white.xl4.bold.center.make() 37 | ``` 38 | 39 | --- 40 | 41 | ## Getting started 42 | 43 | Add it in your root build.gradle at the end of repositories: 44 | 45 | ```gradle 46 | allprojects { 47 | repositories { 48 | ... 49 | maven { url 'https://jitpack.io' } 50 | } 51 | } 52 | 53 | ``` 54 | 55 | Step 2. Add the dependency 56 | 57 | ```gradle 58 | dependencies { 59 | implementation 'com.github.iampawan:VelocityXAndroidCompose:1.0.0-alpha01' 60 | } 61 | ``` 62 | 63 | --- 64 | 65 | ## Usage 66 | 67 | - Check output by running Example App in Android Studio 68 | 69 |
70 | Basic Example of VxText 71 |
 72 | 
 73 | ```kotlin
 74 | "VxText Example".text.white.xl4.p16.bold.center.make()
 75 | ```
 76 | 
 77 | 
78 |
79 | 80 |
81 | Basic Example of VxBox 82 |
 83 | 
 84 | ```kotlin
 85 |  VxBox {
 86 |     "VxBox Example".text.white.bold.p16.xl2.make()
 87 |     }.blue800.wFull().p16.rounded.make()
 88 | ```
 89 | 
 90 | 
91 |
92 | 93 |
94 | Basic Example of VxCard 95 |
 96 | 
 97 | ```kotlin
 98 |  VxCard {
 99 |         "VxCard Example".text.blue800.bold.xl.p20.make()
100 |     }.make()
101 | ```
102 | 
103 | 
104 |
105 | 106 |
107 | Basic Example of VxImage 108 |
109 | 
110 | ```kotlin
111 |   VxImage(R.drawable.flpy).fit.rounded.make()
112 | ```
113 | 
114 | 
115 |
116 | 117 |
118 | Basic Example of VxRow 119 |
120 | 
121 | ```kotlin
122 |    VxRow {
123 |             "VxRow Example".text.white.bold.p16.xl2.make()
124 |             WidthBox(20)
125 |             VxImage(R.drawable.flpy).fit.rounded.make()
126 |         }.blue800.rounded.make()
127 | ```
128 | 
129 | 
130 |
131 | 132 |
133 | Basic Example of VxColumn 134 |
135 | 
136 | ```kotlin
137 |   VxColumn {
138 |             "VxText Example".text.blue800.bold.xl2.make()
139 |             HeightBox(20)
140 |             VxBox {
141 |                 "VxBox Example".text.white.bold.p16.xl2.make()
142 |                 }.blue800.wFull().p16.rounded.make()
143 |             HeightBox(20)
144 |             VxImage(R.drawable.flpy).fit.roundedLg.make()
145 |             HeightBox(20)
146 |             VxRow {
147 |                 "VxRow Example".text.white.bold.p16.xl2.make()
148 |             WidthBox(20)
149 |             VxImage(R.drawable.flpy).fit.rounded.make()
150 |                 }.blue800.rounded.make()
151 |             HeightBox(20)
152 |             VxCard {
153 |                 "VxCard Example".text.blue800.bold.xl.p20.make()
154 |                 }.make()
155 |     }.p16.make()
156 | ```
157 | 
158 | 
159 |
160 | 161 |
162 | Basic Example of VxSpacer 163 |
164 | 
165 | ```kotlin
166 |   VxSpacer().w20().hFull().make()
167 | ```
168 | 
169 | 
170 |
171 | 172 |
173 | Basic Widgets to give space 174 |
175 | 
176 | ```kotlin
177 |   HeightBox(20)
178 |   WidthBox(20)
179 | ```
180 | 
181 | 
182 |
183 | 184 | ## Project Created & Maintained By 185 | 186 | ### Pawan Kumar 187 | 188 | Google Developer Expert for Flutter. Passionate #Flutter, #Android Developer. #Entrepreneur #YouTuber 189 | 190 | 191 | 192 | 193 | 194 | 195 | 196 | # Donate 197 | 198 | > If you found this project helpful or you learned something from the source code and want to thank me, consider buying me a cup of :coffee: 199 | > 200 | > - [PayPal](https://www.paypal.me/imthepk/) 201 | 202 | ### Note: VelocityX is not directly and/or indirectly associated/affiliated with Jetbrains or Google LLC. 203 | 204 | ## Copyright-and-license 205 | 206 | Code and documentation Copyright 2022 Pawan Kumar. Code released under the [Apache License](./LICENSE). Docs released under [Creative Commons](https://creativecommons.org/licenses/by/3.0/). 207 | -------------------------------------------------------------------------------- /VelocityX/.gitignore: -------------------------------------------------------------------------------- 1 | /build -------------------------------------------------------------------------------- /VelocityX/build.gradle: -------------------------------------------------------------------------------- 1 | plugins { 2 | id 'com.android.library' 3 | id 'org.jetbrains.kotlin.android' 4 | } 5 | 6 | android { 7 | compileSdk 33 8 | 9 | defaultConfig { 10 | minSdk 21 11 | targetSdk 33 12 | 13 | testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner" 14 | consumerProguardFiles "consumer-rules.pro" 15 | } 16 | 17 | buildTypes { 18 | release { 19 | minifyEnabled false 20 | proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro' 21 | } 22 | } 23 | compileOptions { 24 | sourceCompatibility JavaVersion.VERSION_1_8 25 | targetCompatibility JavaVersion.VERSION_1_8 26 | } 27 | kotlinOptions { 28 | jvmTarget = '1.8' 29 | } 30 | buildFeatures { 31 | compose true 32 | } 33 | composeOptions { 34 | kotlinCompilerExtensionVersion compose_version 35 | } 36 | } 37 | 38 | dependencies { 39 | 40 | implementation 'androidx.core:core-ktx:1.7.0' 41 | implementation 'androidx.appcompat:appcompat:1.3.0' 42 | implementation 'androidx.compose.material3:material3:1.0.0-alpha14' 43 | implementation "androidx.compose.ui:ui:$compose_version" 44 | implementation "androidx.compose.ui:ui-tooling-preview:$compose_version" 45 | implementation 'androidx.activity:activity-compose:1.3.1' 46 | implementation 'com.google.android.material:material:1.6.1' 47 | testImplementation 'junit:junit:4.13.2' 48 | androidTestImplementation 'androidx.test.ext:junit:1.1.3' 49 | androidTestImplementation 'androidx.test.espresso:espresso-core:3.4.0' 50 | debugImplementation "androidx.compose.ui:ui-test-manifest:$compose_version" 51 | // Test rules and transitive dependencies: 52 | androidTestImplementation("androidx.compose.ui:ui-test-junit4:$compose_version") 53 | // Needed for createComposeRule, but not createAndroidComposeRule: 54 | debugImplementation("androidx.compose.ui:ui-test-manifest:$compose_version") 55 | 56 | 57 | } -------------------------------------------------------------------------------- /VelocityX/consumer-rules.pro: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/iampawan/VelocityXAndroidCompose/59bfe8fdcbb36dc8a46bb2b5afaac7ae9b770ccd/VelocityX/consumer-rules.pro -------------------------------------------------------------------------------- /VelocityX/proguard-rules.pro: -------------------------------------------------------------------------------- 1 | # Add project specific ProGuard rules here. 2 | # You can control the set of applied configuration files using the 3 | # proguardFiles setting in build.gradle. 4 | # 5 | # For more details, see 6 | # http://developer.android.com/guide/developing/tools/proguard.html 7 | 8 | # If your project uses WebView with JS, uncomment the following 9 | # and specify the fully qualified class name to the JavaScript interface 10 | # class: 11 | #-keepclassmembers class fqcn.of.javascript.interface.for.webview { 12 | # public *; 13 | #} 14 | 15 | # Uncomment this to preserve the line number information for 16 | # debugging stack traces. 17 | #-keepattributes SourceFile,LineNumberTable 18 | 19 | # If you keep the line number information, uncomment this to 20 | # hide the original source file name. 21 | #-renamesourcefileattribute SourceFile -------------------------------------------------------------------------------- /VelocityX/src/androidTest/java/dev/codepur/velocityx/ExampleInstrumentedTest.kt: -------------------------------------------------------------------------------- 1 | package dev.codepur.velocityx 2 | 3 | import androidx.test.platform.app.InstrumentationRegistry 4 | import androidx.test.ext.junit.runners.AndroidJUnit4 5 | 6 | import org.junit.Test 7 | import org.junit.runner.RunWith 8 | 9 | import org.junit.Assert.* 10 | 11 | /** 12 | * Instrumented test, which will execute on an Android device. 13 | * 14 | * See [testing documentation](http://d.android.com/tools/testing). 15 | */ 16 | @RunWith(AndroidJUnit4::class) 17 | class ExampleInstrumentedTest { 18 | @Test 19 | fun useAppContext() { 20 | // Context of the app under test. 21 | val appContext = InstrumentationRegistry.getInstrumentation().targetContext 22 | assertEquals("dev.codepur.velocityx.test", appContext.packageName) 23 | } 24 | } -------------------------------------------------------------------------------- /VelocityX/src/androidTest/java/dev/codepur/velocityx/Theme.kt: -------------------------------------------------------------------------------- 1 | package dev.codepur.velocityx 2 | 3 | import android.app.Activity 4 | import android.os.Build 5 | import androidx.compose.foundation.isSystemInDarkTheme 6 | import androidx.compose.material3.* 7 | import androidx.compose.runtime.Composable 8 | import androidx.compose.runtime.SideEffect 9 | import androidx.compose.ui.graphics.Color 10 | import androidx.compose.ui.graphics.toArgb 11 | import androidx.compose.ui.platform.LocalContext 12 | import androidx.compose.ui.platform.LocalView 13 | import androidx.core.view.ViewCompat 14 | 15 | val Purple80 = Color(0xFFD0BCFF) 16 | val PurpleGrey80 = Color(0xFFCCC2DC) 17 | val Pink80 = Color(0xFFEFB8C8) 18 | 19 | val Purple40 = Color(0xFF6650a4) 20 | val PurpleGrey40 = Color(0xFF625b71) 21 | val Pink40 = Color(0xFF7D5260) 22 | 23 | private val DarkColorScheme = darkColorScheme( 24 | primary = Purple80, 25 | secondary = PurpleGrey80, 26 | tertiary = Pink80 27 | ) 28 | 29 | private val LightColorScheme = lightColorScheme( 30 | primary = Purple40, 31 | secondary = PurpleGrey40, 32 | tertiary = Pink40 33 | 34 | /* Other default colors to override 35 | background = Color(0xFFFFFBFE), 36 | surface = Color(0xFFFFFBFE), 37 | onPrimary = Color.White, 38 | onSecondary = Color.White, 39 | onTertiary = Color.White, 40 | onBackground = Color(0xFF1C1B1F), 41 | onSurface = Color(0xFF1C1B1F), 42 | */ 43 | ) 44 | 45 | @Composable 46 | fun vxTheme( 47 | darkTheme: Boolean = isSystemInDarkTheme(), 48 | // Dynamic color is available on Android 12+ 49 | dynamicColor: Boolean = true, 50 | content: @Composable () -> Unit 51 | ) { 52 | val colorScheme = when { 53 | dynamicColor && Build.VERSION.SDK_INT >= Build.VERSION_CODES.S -> { 54 | val context = LocalContext.current 55 | if (darkTheme) dynamicDarkColorScheme(context) else dynamicLightColorScheme(context) 56 | } 57 | darkTheme -> DarkColorScheme 58 | else -> LightColorScheme 59 | } 60 | val view = LocalView.current 61 | if (!view.isInEditMode) { 62 | SideEffect { 63 | (view.context as Activity).window.statusBarColor = colorScheme.primary.toArgb() 64 | ViewCompat.getWindowInsetsController(view)?.isAppearanceLightStatusBars = darkTheme 65 | } 66 | } 67 | 68 | MaterialTheme( 69 | colorScheme = colorScheme, 70 | content = content 71 | ) 72 | } -------------------------------------------------------------------------------- /VelocityX/src/androidTest/java/dev/codepur/velocityx/VxTextTest.kt: -------------------------------------------------------------------------------- 1 | package dev.codepur.velocityx 2 | 3 | import androidx.compose.foundation.layout.fillMaxSize 4 | import androidx.compose.material3.MaterialTheme 5 | import androidx.compose.material3.Surface 6 | import androidx.compose.runtime.Composable 7 | import androidx.compose.ui.Modifier 8 | import androidx.compose.ui.test.assertIsDisplayed 9 | import androidx.compose.ui.test.junit4.createComposeRule 10 | import androidx.compose.ui.test.onNodeWithText 11 | import dev.codepur.velocityx.compose.text 12 | import org.junit.Rule 13 | import org.junit.Test 14 | 15 | class VxTextTest { 16 | 17 | @get:Rule 18 | val composeTestRule = createComposeRule() 19 | // use createAndroidComposeRule() if you need access to 20 | // an activity 21 | 22 | @Test 23 | fun myTest() { 24 | // Start the app 25 | composeTestRule.setContent { 26 | vxTheme { 27 | Surface( 28 | modifier = Modifier.fillMaxSize(), 29 | color = MaterialTheme.colorScheme.surface 30 | ) { 31 | greeting("Android") 32 | } 33 | } 34 | } 35 | composeTestRule.onNodeWithText("Hello Android") 36 | .assertIsDisplayed() 37 | } 38 | 39 | 40 | @Composable 41 | fun greeting(name: String) { 42 | "Hello $name".text.center.make() 43 | } 44 | } -------------------------------------------------------------------------------- /VelocityX/src/main/AndroidManifest.xml: -------------------------------------------------------------------------------- 1 | 2 | 4 | 5 | -------------------------------------------------------------------------------- /VelocityX/src/main/java/dev/codepur/velocityx/Vx.kt: -------------------------------------------------------------------------------- 1 | package dev.codepur.velocityx 2 | 3 | import androidx.compose.foundation.layout.PaddingValues 4 | import androidx.compose.ui.graphics.Color 5 | import androidx.compose.ui.unit.Dp 6 | import androidx.compose.ui.unit.dp 7 | import java.util.* 8 | 9 | class Vx { 10 | 11 | /// Pixel Values 12 | companion object { 13 | val dp0: Dp = 0.0.dp 14 | val dp2: Dp = 2.0.dp 15 | val dp1: Dp = 1.0.dp 16 | val dp3: Dp = 3.0.dp 17 | val dp4: Dp = 4.0.dp 18 | val dp5: Dp = 5.0.dp 19 | val dp6: Dp = 6.0.dp 20 | val dp8: Dp = 8.0.dp 21 | val dp10: Dp = 10.0.dp 22 | val dp12: Dp = 12.0.dp 23 | val dp14: Dp = 14.0.dp 24 | val dp16: Dp = 16.0.dp 25 | val dp20: Dp = 20.0.dp 26 | val dp24: Dp = 24.0.dp 27 | val dp32: Dp = 32.0.dp 28 | val dp40: Dp = 40.0.dp 29 | val dp48: Dp = 48.0.dp 30 | val dp56: Dp = 56.0.dp 31 | val dp64: Dp = 64.0.dp 32 | 33 | fun dp(value: Number): Dp = value.toDouble().dp 34 | 35 | ///Colors 36 | const val blackHex: String = "#000000" 37 | const val whiteHex: String = "#ffffff" 38 | 39 | val black: Color = Color(0xFF000000) 40 | val white: Color = Color(0xFFFFFFFF) 41 | 42 | ///Gray Colors 43 | const val grayHex50: String = "#f9fafb" 44 | const val grayHex100: String = "#f3f4f6" 45 | const val grayHex200: String = "#e5e7eb" 46 | const val grayHex300: String = "#d1d5db" 47 | const val grayHex400: String = "#9ca3af" 48 | const val grayHex500: String = "#6b7280" 49 | const val grayHex600: String = "#4b5563" 50 | const val grayHex700: String = "#374151" 51 | const val grayHex800: String = "#1f2937" 52 | const val grayHex900: String = "#111827" 53 | 54 | val gray50: Color = Color(0xFFf9fafb) 55 | val gray100: Color = Color(0xFFf3f4f6) 56 | val gray200: Color = Color(0xFFe5e7eb) 57 | val gray300: Color = Color(0xFFd1d5db) 58 | val gray400: Color = Color(0xFF9ca3af) 59 | val gray500: Color = Color(0xFF6b7280) 60 | val gray600: Color = Color(0xFF4b5563) 61 | val gray700: Color = Color(0xFF374151) 62 | val gray800: Color = Color(0xFF1f2937) 63 | val gray900: Color = Color(0xFF111827) 64 | 65 | // Slate Colors 66 | const val slateHex50: String = "#f8fafc" 67 | const val slateHex100: String = "#f1f5f9" 68 | const val slateHex200: String = "#e2e8f0" 69 | const val slateHex300: String = "#cbd5e1" 70 | const val slateHex400: String = "#94a3b8" 71 | const val slateHex500: String = "#64748b" 72 | const val slateHex600: String = "#475569" 73 | const val slateHex700: String = "#334155" 74 | const val slateHex800: String = "#1e293b" 75 | const val slateHex900: String = "#0f172a" 76 | 77 | val slate50: Color = Color(0xFFf8fafc) 78 | val slate100: Color = Color(0xFFf1f5f9) 79 | val slate200: Color = Color(0xFFe2e8f0) 80 | val slate300: Color = Color(0xFFcbd5e1) 81 | val slate400: Color = Color(0xFF94a3b8) 82 | val slate500: Color = Color(0xFF64748b) 83 | val slate600: Color = Color(0xFF475569) 84 | val slate700: Color = Color(0xFF334155) 85 | val slate800: Color = Color(0xFF1e293b) 86 | val slate900: Color = Color(0xFF0f172a) 87 | 88 | // Zinc Colors 89 | const val zincHex50: String = "#fafafa" 90 | const val zincHex100: String = "#f4f4f5" 91 | const val zincHex200: String = "#e4e4e7" 92 | const val zincHex300: String = "#d4d4d8" 93 | const val zincHex400: String = "#a1a1aa" 94 | const val zincHex500: String = "#71717a" 95 | const val zincHex600: String = "#52525b" 96 | const val zincHex700: String = "#3f3f46" 97 | const val zincHex800: String = "#27272a" 98 | const val zincHex900: String = "#18181b" 99 | 100 | val zinc50: Color = Color(0xFFfafafa) 101 | val zinc100: Color = Color(0xFFf4f4f5) 102 | val zinc200: Color = Color(0xFFe4e4e7) 103 | val zinc300: Color = Color(0xFFd4d4d8) 104 | val zinc400: Color = Color(0xFFa1a1aa) 105 | val zinc500: Color = Color(0xFF71717a) 106 | val zinc600: Color = Color(0xFF52525b) 107 | val zinc700: Color = Color(0xFF3f3f46) 108 | val zinc800: Color = Color(0xFF27272a) 109 | val zinc900: Color = Color(0xFF18181b) 110 | 111 | // Stone Colors 112 | const val stoneHex50: String = "#FAFAF9" 113 | const val stoneHex100: String = "#F5F5F4" 114 | const val stoneHex200: String = "#E7E5E4" 115 | const val stoneHex300: String = "#D6D3D1" 116 | const val stoneHex400: String = "#A8A29E" 117 | const val stoneHex500: String = "#78716C" 118 | const val stoneHex600: String = "#57534E" 119 | const val stoneHex700: String = "#44403C" 120 | const val stoneHex800: String = "#292524" 121 | const val stoneHex900: String = "#1C1917" 122 | 123 | val stone50: Color = Color(0xFFFAFAF9) 124 | val stone100: Color = Color(0xFFF5F5F4) 125 | val stone200: Color = Color(0xFFE7E5E4) 126 | val stone300: Color = Color(0xFFD6D3D1) 127 | val stone400: Color = Color(0xFFA8A29E) 128 | val stone500: Color = Color(0xFF78716C) 129 | val stone600: Color = Color(0xFF57534E) 130 | val stone700: Color = Color(0xFF44403C) 131 | val stone800: Color = Color(0xFF292524) 132 | val stone900: Color = Color(0xFF1C1917) 133 | 134 | // Neutral Colors 135 | const val neutralHex50: String = "#fafafa" 136 | const val neutralHex100: String = "#f5f5f5" 137 | const val neutralHex200: String = "#e5e5e5" 138 | const val neutralHex300: String = "#d4d4d4" 139 | const val neutralHex400: String = "#a3a3a3" 140 | const val neutralHex500: String = "#737373" 141 | const val neutralHex600: String = "#525252" 142 | const val neutralHex700: String = "#404040" 143 | const val neutralHex800: String = "#262626" 144 | const val neutralHex900: String = "#171717" 145 | 146 | val neutral50: Color = Color(0xFFfafafa) 147 | val neutral100: Color = Color(0xFFf5f5f5) 148 | val neutral200: Color = Color(0xFFe5e5e5) 149 | val neutral300: Color = Color(0xFFd4d4d4) 150 | val neutral400: Color = Color(0xFFa3a3a3) 151 | val neutral500: Color = Color(0xFF737373) 152 | val neutral600: Color = Color(0xFF525252) 153 | val neutral700: Color = Color(0xFF404040) 154 | val neutral800: Color = Color(0xFF262626) 155 | val neutral900: Color = Color(0xFF171717) 156 | 157 | ///Red Colors 158 | const val redHex50: String = "#FEF2F2" 159 | const val redHex100: String = "#FEE2E2" 160 | const val redHex200: String = "#FECACA" 161 | const val redHex300: String = "#FCA5A5" 162 | const val redHex400: String = "#F87171" 163 | const val redHex500: String = "#EF4444" 164 | const val redHex600: String = "#DC2626" 165 | const val redHex700: String = "#B91C1C" 166 | const val redHex800: String = "#991B1B" 167 | const val redHex900: String = "#7F1D1D" 168 | 169 | val red50: Color = Color(0xFFFEF2F2) 170 | val red100: Color = Color(0xFFFEE2E2) 171 | val red200: Color = Color(0xFFFECACA) 172 | val red300: Color = Color(0xFFFCA5A5) 173 | val red400: Color = Color(0xFFF87171) 174 | val red500: Color = Color(0xFFEF4444) 175 | val red600: Color = Color(0xFFDC2626) 176 | val red700: Color = Color(0xFFB91C1C) 177 | val red800: Color = Color(0xFF991B1B) 178 | val red900: Color = Color(0xFF7F1D1D) 179 | 180 | ///Orange Colors 181 | const val orangeHex50: String = "#FFF7ED" 182 | const val orangeHex100: String = "#FFEDD5" 183 | const val orangeHex200: String = "#FED7AA" 184 | const val orangeHex300: String = "#FDBA74" 185 | const val orangeHex400: String = "#FB923C" 186 | const val orangeHex500: String = "#F97316" 187 | const val orangeHex600: String = "#EA580C" 188 | const val orangeHex700: String = "#C2410C" 189 | const val orangeHex800: String = "#9A3412" 190 | const val orangeHex900: String = "#7C2D12" 191 | 192 | val orange50: Color = Color(0xFFFFF7ED) 193 | val orange100: Color = Color(0xFFFFEDD5) 194 | val orange200: Color = Color(0xFFFED7AA) 195 | val orange300: Color = Color(0xFFFDBA74) 196 | val orange400: Color = Color(0xFFFB923C) 197 | val orange500: Color = Color(0xFFF97316) 198 | val orange600: Color = Color(0xFFEA580C) 199 | val orange700: Color = Color(0xFFC2410C) 200 | val orange800: Color = Color(0xFF9A3412) 201 | val orange900: Color = Color(0xFF7C2D12) 202 | 203 | ///Amber Colors 204 | const val amberHex50: String = "#FFFBEB" 205 | const val amberHex100: String = "#FEF3C7" 206 | const val amberHex200: String = "#FDE68A" 207 | const val amberHex300: String = "#FCD34D" 208 | const val amberHex400: String = "#FBBF24" 209 | const val amberHex500: String = "#F59E0B" 210 | const val amberHex600: String = "#D97706" 211 | const val amberHex700: String = "#B45309" 212 | const val amberHex800: String = "#92400E" 213 | const val amberHex900: String = "#78350F" 214 | 215 | val amber50: Color = Color(0xFFFFFBEB) 216 | val amber100: Color = Color(0xFFFEF3C7) 217 | val amber200: Color = Color(0xFFFDE68A) 218 | val amber300: Color = Color(0xFFFCD34D) 219 | val amber400: Color = Color(0xFFFBBF24) 220 | val amber500: Color = Color(0xFFF59E0B) 221 | val amber600: Color = Color(0xFFD97706) 222 | val amber700: Color = Color(0xFFB45309) 223 | val amber800: Color = Color(0xFF92400E) 224 | val amber900: Color = Color(0xFF78350F) 225 | 226 | ///Yellow Colors 227 | const val yellowHex50: String = "#FEFCE8" 228 | const val yellowHex100: String = "#FEF9C3" 229 | const val yellowHex200: String = "#FEF08A" 230 | const val yellowHex300: String = "#FDE047" 231 | const val yellowHex400: String = "#FACC15" 232 | const val yellowHex500: String = "#EAB308" 233 | const val yellowHex600: String = "#CA8A04" 234 | const val yellowHex700: String = "#A16207" 235 | const val yellowHex800: String = "#854D0E" 236 | const val yellowHex900: String = "#713F12" 237 | 238 | val yellow50: Color = Color(0xFFFEFCE8) 239 | val yellow100: Color = Color(0xFFFEF9C3) 240 | val yellow200: Color = Color(0xFFFEF08A) 241 | val yellow300: Color = Color(0xFFFDE047) 242 | val yellow400: Color = Color(0xFFFACC15) 243 | val yellow500: Color = Color(0xFFEAB308) 244 | val yellow600: Color = Color(0xFFCA8A04) 245 | val yellow700: Color = Color(0xFFA16207) 246 | val yellow800: Color = Color(0xFF854D0E) 247 | val yellow900: Color = Color(0xFF713F12) 248 | 249 | ///Lime Colors 250 | const val limeHex50: String = "#F7FEE7" 251 | const val limeHex100: String = "#ECFCCB" 252 | const val limeHex200: String = "#D9F99D" 253 | const val limeHex300: String = "#BEF264" 254 | const val limeHex400: String = "#A3E635" 255 | const val limeHex500: String = "#84CC16" 256 | const val limeHex600: String = "#65A30D" 257 | const val limeHex700: String = "#4D7C0F" 258 | const val limeHex800: String = "#3F6212" 259 | const val limeHex900: String = "#365314" 260 | 261 | val lime50: Color = Color(0xFFF7FEE7) 262 | val lime100: Color = Color(0xFFECFCCB) 263 | val lime200: Color = Color(0xFFD9F99D) 264 | val lime300: Color = Color(0xFFBEF264) 265 | val lime400: Color = Color(0xFFA3E635) 266 | val lime500: Color = Color(0xFF84CC16) 267 | val lime600: Color = Color(0xFF65A30D) 268 | val lime700: Color = Color(0xFF4D7C0F) 269 | val lime800: Color = Color(0xFF3F6212) 270 | val lime900: Color = Color(0xFF365314) 271 | 272 | ///Green Colors 273 | const val greenHex50: String = "#F0FDF4" 274 | const val greenHex100: String = "#DCFCE7" 275 | const val greenHex200: String = "#BBF7D0" 276 | const val greenHex300: String = "#86EFAC" 277 | const val greenHex400: String = "#4ADE80" 278 | const val greenHex500: String = "#22C55E" 279 | const val greenHex600: String = "#16A34A" 280 | const val greenHex700: String = "#15803D" 281 | const val greenHex800: String = "#166534" 282 | const val greenHex900: String = "#14532D" 283 | 284 | val green50: Color = Color(0xFFF0FDF4) 285 | val green100: Color = Color(0xFFDCFCE7) 286 | val green200: Color = Color(0xFFBBF7D0) 287 | val green300: Color = Color(0xFF86EFAC) 288 | val green400: Color = Color(0xFF4ADE80) 289 | val green500: Color = Color(0xFF22C55E) 290 | val green600: Color = Color(0xFF16A34A) 291 | val green700: Color = Color(0xFF15803D) 292 | val green800: Color = Color(0xFF166534) 293 | val green900: Color = Color(0xFF14532D) 294 | 295 | ///Emerald Colors 296 | const val emeraldHex50: String = "#ECFDF5" 297 | const val emeraldHex100: String = "#D1FAE5" 298 | const val emeraldHex200: String = "#A7F3D0" 299 | const val emeraldHex300: String = "#6EE7B7" 300 | const val emeraldHex400: String = "#34D399" 301 | const val emeraldHex500: String = "#10B981" 302 | const val emeraldHex600: String = "#059669" 303 | const val emeraldHex700: String = "#047857" 304 | const val emeraldHex800: String = "#065F46" 305 | const val emeraldHex900: String = "#064E3B" 306 | 307 | val emerald50: Color = Color(0xFFECFDF5) 308 | val emerald100: Color = Color(0xFFD1FAE5) 309 | val emerald200: Color = Color(0xFFA7F3D0) 310 | val emerald300: Color = Color(0xFF6EE7B7) 311 | val emerald400: Color = Color(0xFF34D399) 312 | val emerald500: Color = Color(0xFF10B981) 313 | val emerald600: Color = Color(0xFF059669) 314 | val emerald700: Color = Color(0xFF047857) 315 | val emerald800: Color = Color(0xFF065F46) 316 | val emerald900: Color = Color(0xFF064E3B) 317 | 318 | ///Teal Colors 319 | const val tealHex50: String = "#F0FDFA" 320 | const val tealHex100: String = "#CCFBF1" 321 | const val tealHex200: String = "#99F6E4" 322 | const val tealHex300: String = "#5EEAD4" 323 | const val tealHex400: String = "#2DD4BF" 324 | const val tealHex500: String = "#14B8A6" 325 | const val tealHex600: String = "#0D9488" 326 | const val tealHex700: String = "#0F766E" 327 | const val tealHex800: String = "#115E59" 328 | const val tealHex900: String = "#134E4A" 329 | 330 | val teal50: Color = Color(0xFFF0FDFA) 331 | val teal100: Color = Color(0xFFCCFBF1) 332 | val teal200: Color = Color(0xFF99F6E4) 333 | val teal300: Color = Color(0xFF5EEAD4) 334 | val teal400: Color = Color(0xFF2DD4BF) 335 | val teal500: Color = Color(0xFF14B8A6) 336 | val teal600: Color = Color(0xFF0D9488) 337 | val teal700: Color = Color(0xFF0F766E) 338 | val teal800: Color = Color(0xFF115E59) 339 | val teal900: Color = Color(0xFF134E4A) 340 | 341 | ///Cyan Colors 342 | const val cyanHex50: String = "#ECFEFF" 343 | const val cyanHex100: String = "#CFFAFE" 344 | const val cyanHex200: String = "#A5F3FC" 345 | const val cyanHex300: String = "#67E8F9" 346 | const val cyanHex400: String = "#22D3EE" 347 | const val cyanHex500: String = "#06B6D4" 348 | const val cyanHex600: String = "#0891B2" 349 | const val cyanHex700: String = "#0E7490" 350 | const val cyanHex800: String = "#155E75" 351 | const val cyanHex900: String = "#164E63" 352 | 353 | val cyan50: Color = Color(0xFFECFEFF) 354 | val cyan100: Color = Color(0xFFCFFAFE) 355 | val cyan200: Color = Color(0xFFA5F3FC) 356 | val cyan300: Color = Color(0xFF67E8F9) 357 | val cyan400: Color = Color(0xFF22D3EE) 358 | val cyan500: Color = Color(0xFF06B6D4) 359 | val cyan600: Color = Color(0xFF0891B2) 360 | val cyan700: Color = Color(0xFF0E7490) 361 | val cyan800: Color = Color(0xFF155E75) 362 | val cyan900: Color = Color(0xFF164E63) 363 | 364 | ///Sky Colors 365 | const val skyHex50: String = "#F0F9FF" 366 | const val skyHex100: String = "#E0F2FE" 367 | const val skyHex200: String = "#BAE6FD" 368 | const val skyHex300: String = "#7DD3FC" 369 | const val skyHex400: String = "#38BDF8" 370 | const val skyHex500: String = "#0EA5E9" 371 | const val skyHex600: String = "#0284C7" 372 | const val skyHex700: String = "#0369A1" 373 | const val skyHex800: String = "#075985" 374 | const val skyHex900: String = "#0C4A6E" 375 | 376 | val sky50: Color = Color(0xFFF0F9FF) 377 | val sky100: Color = Color(0xFFE0F2FE) 378 | val sky200: Color = Color(0xFFBAE6FD) 379 | val sky300: Color = Color(0xFF7DD3FC) 380 | val sky400: Color = Color(0xFF38BDF8) 381 | val sky500: Color = Color(0xFF0EA5E9) 382 | val sky600: Color = Color(0xFF0284C7) 383 | val sky700: Color = Color(0xFF0369A1) 384 | val sky800: Color = Color(0xFF075985) 385 | val sky900: Color = Color(0xFF0C4A6E) 386 | 387 | ///Blue Colors 388 | const val blueHex50: String = "#EFF6FF" 389 | const val blueHex100: String = "#DBEAFE" 390 | const val blueHex200: String = "#BFDBFE" 391 | const val blueHex300: String = "#93C5FD" 392 | const val blueHex400: String = "#60A5FA" 393 | const val blueHex500: String = "#3B82F6" 394 | const val blueHex600: String = "#2563EB" 395 | const val blueHex700: String = "#1D4ED8" 396 | const val blueHex800: String = "#1E40AF" 397 | const val blueHex900: String = "#1E3A8A" 398 | 399 | val blue50: Color = Color(0xFFEFF6FF) 400 | val blue100: Color = Color(0xFFDBEAFE) 401 | val blue200: Color = Color(0xFFBFDBFE) 402 | val blue300: Color = Color(0xFF93C5FD) 403 | val blue400: Color = Color(0xFF60A5FA) 404 | val blue500: Color = Color(0xFF3B82F6) 405 | val blue600: Color = Color(0xFF2563EB) 406 | val blue700: Color = Color(0xFF1D4ED8) 407 | val blue800: Color = Color(0xFF1E40AF) 408 | val blue900: Color = Color(0xFF1E3A8A) 409 | 410 | ///Indigo Colors 411 | const val indigoHex50: String = "#EEF2FF" 412 | const val indigoHex100: String = "#E0E7FF" 413 | const val indigoHex200: String = "#C7D2FE" 414 | const val indigoHex300: String = "#A5B4FC" 415 | const val indigoHex400: String = "#818CF8" 416 | const val indigoHex500: String = "#6366F1" 417 | const val indigoHex600: String = "#4F46E5" 418 | const val indigoHex700: String = "#4338CA" 419 | const val indigoHex800: String = "#3730A3" 420 | const val indigoHex900: String = "#312E81" 421 | 422 | val indigo50: Color = Color(0xFFEEF2FF) 423 | val indigo100: Color = Color(0xFFE0E7FF) 424 | val indigo200: Color = Color(0xFFC7D2FE) 425 | val indigo300: Color = Color(0xFFA5B4FC) 426 | val indigo400: Color = Color(0xFF818CF8) 427 | val indigo500: Color = Color(0xFF6366F1) 428 | val indigo600: Color = Color(0xFF4F46E5) 429 | val indigo700: Color = Color(0xFF4338CA) 430 | val indigo800: Color = Color(0xFF3730A3) 431 | val indigo900: Color = Color(0xFF312E81) 432 | 433 | ///Violet Colors 434 | const val violetHex50: String = "#F5F3FF" 435 | const val violetHex100: String = "#EDE9FE" 436 | const val violetHex200: String = "#DDD6FE" 437 | const val violetHex300: String = "#C4B5FD" 438 | const val violetHex400: String = "#A78BFA" 439 | const val violetHex500: String = "#8B5CF6" 440 | const val violetHex600: String = "#7C3AED" 441 | const val violetHex700: String = "#6D28D9" 442 | const val violetHex800: String = "#5B21B6" 443 | const val violetHex900: String = "#4C1D95" 444 | 445 | val violet50: Color = Color(0xFFF5F3FF) 446 | val violet100: Color = Color(0xFFEDE9FE) 447 | val violet200: Color = Color(0xFFDDD6FE) 448 | val violet300: Color = Color(0xFFC4B5FD) 449 | val violet400: Color = Color(0xFFA78BFA) 450 | val violet500: Color = Color(0xFF8B5CF6) 451 | val violet600: Color = Color(0xFF7C3AED) 452 | val violet700: Color = Color(0xFF6D28D9) 453 | val violet800: Color = Color(0xFF5B21B6) 454 | val violet900: Color = Color(0xFF4C1D95) 455 | 456 | ///Purple Colors 457 | const val purpleHex50: String = "#FAF5FF" 458 | const val purpleHex100: String = "#F3E8FF" 459 | const val purpleHex200: String = "#E9D5FF" 460 | const val purpleHex300: String = "#D8B4FE" 461 | const val purpleHex400: String = "#C084FC" 462 | const val purpleHex500: String = "#A855F7" 463 | const val purpleHex600: String = "#9333EA" 464 | const val purpleHex700: String = "#7E22CE" 465 | const val purpleHex800: String = "#6B21A8" 466 | const val purpleHex900: String = "#581C87" 467 | 468 | val purple50: Color = Color(0xFFFAF5FF) 469 | val purple100: Color = Color(0xFFF3E8FF) 470 | val purple200: Color = Color(0xFFE9D5FF) 471 | val purple300: Color = Color(0xFFD8B4FE) 472 | val purple400: Color = Color(0xFFC084FC) 473 | val purple500: Color = Color(0xFFA855F7) 474 | val purple600: Color = Color(0xFF9333EA) 475 | val purple700: Color = Color(0xFF7E22CE) 476 | val purple800: Color = Color(0xFF6B21A8) 477 | val purple900: Color = Color(0xFF581C87) 478 | 479 | ///Fuchsia Colors 480 | const val fuchsiaHex50: String = "#FDF4FF" 481 | const val fuchsiaHex100: String = "#FAE8FF" 482 | const val fuchsiaHex200: String = "#F5D0FE" 483 | const val fuchsiaHex300: String = "#F0ABFC" 484 | const val fuchsiaHex400: String = "#E879F9" 485 | const val fuchsiaHex500: String = "#D946EF" 486 | const val fuchsiaHex600: String = "#C026D3" 487 | const val fuchsiaHex700: String = "#A21CAF" 488 | const val fuchsiaHex800: String = "#86198F" 489 | const val fuchsiaHex900: String = "#701A75" 490 | 491 | val fuchsia50: Color = Color(0xFFFDF4FF) 492 | val fuchsia100: Color = Color(0xFFFAE8FF) 493 | val fuchsia200: Color = Color(0xFFF5D0FE) 494 | val fuchsia300: Color = Color(0xFFF0ABFC) 495 | val fuchsia400: Color = Color(0xFFE879F9) 496 | val fuchsia500: Color = Color(0xFFD946EF) 497 | val fuchsia600: Color = Color(0xFFC026D3) 498 | val fuchsia700: Color = Color(0xFFA21CAF) 499 | val fuchsia800: Color = Color(0xFF86198F) 500 | val fuchsia900: Color = Color(0xFF701A75) 501 | 502 | ///Pink Colors 503 | const val pinkHex50: String = "#FDF2F8" 504 | const val pinkHex100: String = "#FCE7F3" 505 | const val pinkHex200: String = "#FBCFE8" 506 | const val pinkHex300: String = "#F9A8D4" 507 | const val pinkHex400: String = "#F472B6" 508 | const val pinkHex500: String = "#EC4899" 509 | const val pinkHex600: String = "#DB2777" 510 | const val pinkHex700: String = "#BE185D" 511 | const val pinkHex800: String = "#9D174D" 512 | const val pinkHex900: String = "#831843" 513 | 514 | val pink50: Color = Color(0xFFFDF2F8) 515 | val pink100: Color = Color(0xFFFCE7F3) 516 | val pink200: Color = Color(0xFFFBCFE8) 517 | val pink300: Color = Color(0xFFF9A8D4) 518 | val pink400: Color = Color(0xFFF472B6) 519 | val pink500: Color = Color(0xFFEC4899) 520 | val pink600: Color = Color(0xFFDB2777) 521 | val pink700: Color = Color(0xFFBE185D) 522 | val pink800: Color = Color(0xFF9D174D) 523 | val pink900: Color = Color(0xFF831843) 524 | 525 | ///Rose Colors 526 | const val roseHex50: String = "#FFF1F2" 527 | const val roseHex100: String = "#FFE4E6" 528 | const val roseHex200: String = "#FECDD3" 529 | const val roseHex300: String = "#FDA4AF" 530 | const val roseHex400: String = "#FB7185" 531 | const val roseHex500: String = "#F43F5E" 532 | const val roseHex600: String = "#E11D48" 533 | const val roseHex700: String = "#BE123C" 534 | const val roseHex800: String = "#9F1239" 535 | const val roseHex900: String = "#881337" 536 | 537 | val rose50: Color = Color(0xFFFFF1F2) 538 | val rose100: Color = Color(0xFFFFE4E6) 539 | val rose200: Color = Color(0xFFFECDD3) 540 | val rose300: Color = Color(0xFFFDA4AF) 541 | val rose400: Color = Color(0xFFFB7185) 542 | val rose500: Color = Color(0xFFF43F5E) 543 | val rose600: Color = Color(0xFFE11D48) 544 | val rose700: Color = Color(0xFFBE123C) 545 | val rose800: Color = Color(0xFF9F1239) 546 | val rose900: Color = Color(0xFF881337) 547 | 548 | 549 | /// Get color from the hex value 550 | fun hexToColor(code: String): Color = 551 | Color(android.graphics.Color.parseColor(code)) 552 | 553 | /// Get Random Non-Primary Color 554 | val randomOpaqueColor: Color 555 | get() = Color(Random().nextInt(0xffffff)).copy(alpha = 1.0f) 556 | 557 | 558 | ///Padding 559 | /// All Fixed EdgeInsets 560 | var m0: PaddingValues? = PaddingValues(all = 0.dp) 561 | var m1: PaddingValues? = PaddingValues(all = 1.dp) 562 | var m2: PaddingValues? = PaddingValues(all = 2.dp) 563 | 564 | } 565 | } -------------------------------------------------------------------------------- /VelocityX/src/main/java/dev/codepur/velocityx/VxWidgetBuilder.kt: -------------------------------------------------------------------------------- 1 | package dev.codepur.velocityx 2 | 3 | import android.annotation.SuppressLint 4 | import androidx.compose.runtime.Composable 5 | 6 | interface VxWidgetBuilder { 7 | 8 | @SuppressLint("ComposableNaming") 9 | @Composable 10 | fun make() 11 | } 12 | 13 | -------------------------------------------------------------------------------- /VelocityX/src/main/java/dev/codepur/velocityx/compose/VxBox.kt: -------------------------------------------------------------------------------- 1 | package dev.codepur.velocityx.compose 2 | 3 | import android.annotation.SuppressLint 4 | import androidx.compose.foundation.background 5 | import androidx.compose.foundation.layout.Box 6 | import androidx.compose.foundation.layout.BoxScope 7 | import androidx.compose.runtime.Composable 8 | import androidx.compose.ui.Alignment 9 | import androidx.compose.ui.Modifier 10 | import dev.codepur.velocityx.VxWidgetBuilder 11 | import dev.codepur.velocityx.mixin.* 12 | 13 | open class VxBoxAddOn( 14 | colorMixin: IVxColorMixin = VxColorMixin(), 15 | alignmentMixin: IVxAlignmentMixin = VxAlignmentMixin(), 16 | modifierMixin: IVxModifierMixin = VxModifierMixin(), 17 | 18 | ) : 19 | IVxColorMixin by colorMixin, IVxAlignmentMixin by alignmentMixin, 20 | IVxModifierMixin by modifierMixin 21 | 22 | class VxBox( 23 | private val children: @Composable BoxScope.() -> Unit, 24 | ) : VxWidgetBuilder, VxBoxAddOn() { 25 | 26 | init { 27 | setChildToColor(this) 28 | setChildForAlignment(this) 29 | setChildForModifier(this) 30 | 31 | } 32 | 33 | @SuppressLint("ComposableNaming") 34 | @Composable 35 | override fun make() { 36 | var currentModifier = velocityModifier ?: Modifier 37 | if (velocityColor != null) { 38 | currentModifier = currentModifier 39 | .background(color = velocityColor!!) 40 | 41 | } 42 | 43 | return Box( 44 | contentAlignment = velocityAlignment ?: Alignment.TopStart, 45 | modifier = currentModifier 46 | ) { 47 | children.invoke(this) 48 | 49 | } 50 | } 51 | 52 | 53 | } 54 | 55 | -------------------------------------------------------------------------------- /VelocityX/src/main/java/dev/codepur/velocityx/compose/VxCard.kt: -------------------------------------------------------------------------------- 1 | package dev.codepur.velocityx.compose 2 | 3 | import android.annotation.SuppressLint 4 | import androidx.compose.foundation.BorderStroke 5 | import androidx.compose.foundation.interaction.MutableInteractionSource 6 | import androidx.compose.foundation.layout.Column 7 | import androidx.compose.foundation.layout.ColumnScope 8 | import androidx.compose.foundation.shape.RoundedCornerShape 9 | import androidx.compose.material3.* 10 | import androidx.compose.runtime.Composable 11 | import androidx.compose.runtime.remember 12 | import androidx.compose.ui.Modifier 13 | import androidx.compose.ui.graphics.Shape 14 | import androidx.compose.ui.unit.dp 15 | import dev.codepur.velocityx.VxWidgetBuilder 16 | import dev.codepur.velocityx.mixin.* 17 | 18 | open class VxCardAddOn( 19 | colorMixin: IVxColorMixin = VxColorMixin(), 20 | alignmentMixin: IVxAlignmentMixin = VxAlignmentMixin(), 21 | modifierMixin: IVxModifierMixin = VxModifierMixin() 22 | ) : 23 | IVxColorMixin by colorMixin, IVxAlignmentMixin by alignmentMixin, 24 | IVxModifierMixin by modifierMixin 25 | 26 | class VxCard( 27 | private val enabled: Boolean = true, 28 | private val shape: Shape = RoundedCornerShape(12.dp), 29 | private val stroke: BorderStroke? = null, 30 | private var elevation: CardElevation? = null, 31 | private var colors: CardColors? = null, 32 | private val onClick: () -> Unit = {}, 33 | private val children: @Composable ColumnScope.() -> Unit, 34 | 35 | 36 | ) : VxWidgetBuilder, VxCardAddOn() { 37 | 38 | init { 39 | setChildToColor(this) 40 | setChildForAlignment(this) 41 | setChildForModifier(this) 42 | 43 | } 44 | 45 | @OptIn(ExperimentalMaterial3Api::class) 46 | @SuppressLint("ComposableNaming") 47 | @Composable 48 | override fun make() { 49 | if (colors == null) { 50 | colors = CardDefaults.cardColors() 51 | } 52 | var currentModifier = velocityModifier ?: Modifier 53 | if (velocityColor != null) { 54 | colors = CardDefaults.cardColors(containerColor = velocityColor!!) 55 | 56 | } 57 | 58 | if (elevation == null) { 59 | elevation = CardDefaults.cardElevation() 60 | } 61 | val interactionSource = remember { MutableInteractionSource() } 62 | return Surface( 63 | onClick = onClick, 64 | modifier = currentModifier, 65 | enabled = enabled, 66 | shape = shape, 67 | color = colors!!.containerColor(enabled).value, 68 | contentColor = colors!!.contentColor(enabled).value, 69 | tonalElevation = elevation!!.tonalElevation(enabled, interactionSource).value, 70 | shadowElevation = elevation!!.shadowElevation(enabled, interactionSource).value, 71 | border = stroke, 72 | interactionSource = interactionSource, 73 | 74 | ) { 75 | Column(content = children) 76 | 77 | } 78 | } 79 | 80 | 81 | } 82 | 83 | -------------------------------------------------------------------------------- /VelocityX/src/main/java/dev/codepur/velocityx/compose/VxColumn.kt: -------------------------------------------------------------------------------- 1 | package dev.codepur.velocityx.compose 2 | 3 | import android.annotation.SuppressLint 4 | import androidx.compose.foundation.background 5 | import androidx.compose.foundation.layout.Arrangement 6 | import androidx.compose.foundation.layout.Column 7 | import androidx.compose.foundation.layout.ColumnScope 8 | import androidx.compose.runtime.Composable 9 | import androidx.compose.ui.Alignment 10 | import androidx.compose.ui.Modifier 11 | import dev.codepur.velocityx.VxWidgetBuilder 12 | import dev.codepur.velocityx.mixin.* 13 | 14 | 15 | open class VxColumnAddOn( 16 | colorMixin: IVxColorMixin = VxColorMixin(), 17 | modifierMixin: IVxModifierMixin = VxModifierMixin(), 18 | rowColumnAlignmentMixin: IVxRowColumnAlignmentMixin = VxRowColumnAlignmentMixin(), 19 | ) : 20 | IVxColorMixin by colorMixin, 21 | IVxModifierMixin by modifierMixin, 22 | IVxRowColumnAlignmentMixin by rowColumnAlignmentMixin 23 | 24 | class VxColumn( 25 | private val children: @Composable ColumnScope.() -> Unit 26 | 27 | ) : VxWidgetBuilder, VxColumnAddOn() { 28 | 29 | init { 30 | setChildToColor(this) 31 | setChildForModifier(this) 32 | setChildForRowColumnAlignment(this) 33 | 34 | } 35 | 36 | @SuppressLint("ComposableNaming") 37 | @Composable 38 | override fun make() { 39 | var currentModifier = velocityModifier ?: Modifier 40 | if (velocityColor != null) { 41 | currentModifier = currentModifier 42 | .background(color = velocityColor!!) 43 | 44 | } 45 | return Column( 46 | verticalArrangement = verticalArrangement ?: Arrangement.Top, 47 | horizontalAlignment = horizontalAlignment ?: Alignment.Start, 48 | modifier = currentModifier, 49 | ) { 50 | children.invoke(this) 51 | 52 | } 53 | } 54 | 55 | 56 | } 57 | 58 | -------------------------------------------------------------------------------- /VelocityX/src/main/java/dev/codepur/velocityx/compose/VxImage.kt: -------------------------------------------------------------------------------- 1 | package dev.codepur.velocityx.compose 2 | 3 | import android.annotation.SuppressLint 4 | import androidx.compose.foundation.Image 5 | import androidx.compose.foundation.background 6 | import androidx.compose.runtime.Composable 7 | import androidx.compose.ui.Alignment 8 | import androidx.compose.ui.Modifier 9 | import androidx.compose.ui.graphics.ColorFilter 10 | import androidx.compose.ui.graphics.DefaultAlpha 11 | import androidx.compose.ui.layout.ContentScale 12 | import androidx.compose.ui.res.painterResource 13 | import dev.codepur.velocityx.VxWidgetBuilder 14 | import dev.codepur.velocityx.mixin.* 15 | 16 | open class VxImageAddOn( 17 | colorMixin: IVxColorMixin = VxColorMixin(), 18 | alignmentMixin: IVxAlignmentMixin = VxAlignmentMixin(), 19 | modifierMixin: IVxModifierMixin = VxModifierMixin() 20 | ) : 21 | IVxColorMixin by colorMixin, IVxAlignmentMixin by alignmentMixin, 22 | IVxModifierMixin by modifierMixin 23 | 24 | class VxImage(private val resId: Int) : VxWidgetBuilder, VxImageAddOn() { 25 | init { 26 | setChildToColor(this) 27 | setChildForAlignment(this) 28 | setChildForModifier(this) 29 | 30 | } 31 | 32 | private var content: String? = null 33 | private var alpha: Float = DefaultAlpha 34 | private var contentScale: ContentScale = ContentScale.Fit 35 | private var velocityColorFilter: ColorFilter? = null 36 | 37 | fun description(value: String): VxImage { 38 | content = value 39 | return this 40 | } 41 | 42 | fun alpha(value: Float): VxImage { 43 | alpha = value 44 | return this 45 | } 46 | 47 | fun colorFilter(value: ColorFilter?): VxImage { 48 | velocityColorFilter = value 49 | return this 50 | } 51 | 52 | val fit: VxImage 53 | get() { 54 | contentScale = ContentScale.Fit 55 | return this 56 | } 57 | 58 | val crop: VxImage 59 | get() { 60 | contentScale = ContentScale.Crop 61 | return this 62 | } 63 | 64 | val fill: VxImage 65 | get() { 66 | contentScale = ContentScale.FillBounds 67 | return this 68 | } 69 | 70 | val fillWidth: VxImage 71 | get() { 72 | contentScale = ContentScale.FillWidth 73 | return this 74 | } 75 | 76 | val fillHeight: VxImage 77 | get() { 78 | contentScale = ContentScale.FillHeight 79 | return this 80 | } 81 | 82 | val fitInside: VxImage 83 | get() { 84 | contentScale = ContentScale.Inside 85 | return this 86 | } 87 | 88 | val none: VxImage 89 | get() { 90 | contentScale = ContentScale.None 91 | return this 92 | } 93 | 94 | 95 | @SuppressLint("ComposableNaming") 96 | @Composable 97 | override fun make() { 98 | var currentModifier = velocityModifier ?: Modifier 99 | if (velocityColor != null) { 100 | currentModifier = currentModifier 101 | .background(color = velocityColor!!) 102 | 103 | } 104 | Image( 105 | painter = painterResource(id = resId), 106 | contentDescription = content ?: "", 107 | alignment = velocityAlignment ?: Alignment.Center, 108 | modifier = currentModifier, 109 | contentScale = contentScale, 110 | alpha = alpha, 111 | colorFilter = velocityColorFilter 112 | ) 113 | } 114 | 115 | 116 | } -------------------------------------------------------------------------------- /VelocityX/src/main/java/dev/codepur/velocityx/compose/VxRow.kt: -------------------------------------------------------------------------------- 1 | package dev.codepur.velocityx.compose 2 | 3 | import android.annotation.SuppressLint 4 | import androidx.compose.foundation.background 5 | import androidx.compose.foundation.layout.Arrangement 6 | import androidx.compose.foundation.layout.Row 7 | import androidx.compose.foundation.layout.RowScope 8 | import androidx.compose.runtime.Composable 9 | import androidx.compose.ui.Alignment 10 | import androidx.compose.ui.Modifier 11 | import dev.codepur.velocityx.VxWidgetBuilder 12 | import dev.codepur.velocityx.mixin.* 13 | 14 | 15 | open class VxRowAddOn( 16 | colorMixin: IVxColorMixin = VxColorMixin(), 17 | modifierMixin: IVxModifierMixin = VxModifierMixin(), 18 | rowColumnAlignmentMixin: IVxRowColumnAlignmentMixin = VxRowColumnAlignmentMixin(), 19 | ) : 20 | IVxColorMixin by colorMixin, 21 | IVxModifierMixin by modifierMixin, 22 | IVxRowColumnAlignmentMixin by rowColumnAlignmentMixin 23 | 24 | class VxRow( 25 | private val children: @Composable RowScope.() -> Unit 26 | 27 | ) : VxWidgetBuilder, VxRowAddOn() { 28 | 29 | init { 30 | setChildToColor(this) 31 | setChildForModifier(this) 32 | setChildForRowColumnAlignment(this) 33 | } 34 | 35 | 36 | @SuppressLint("ComposableNaming") 37 | @Composable 38 | override fun make() { 39 | var currentModifier = velocityModifier ?: Modifier 40 | if (velocityColor != null) { 41 | currentModifier = currentModifier 42 | .background(color = velocityColor!!) 43 | 44 | } 45 | return Row( 46 | verticalAlignment = verticalAlignment ?: Alignment.Top, 47 | horizontalArrangement = horizontalArrangement ?: Arrangement.Start, 48 | modifier = currentModifier, 49 | ) { 50 | children.invoke(this) 51 | 52 | } 53 | } 54 | 55 | 56 | } 57 | 58 | -------------------------------------------------------------------------------- /VelocityX/src/main/java/dev/codepur/velocityx/compose/VxSpacer.kt: -------------------------------------------------------------------------------- 1 | package dev.codepur.velocityx.compose 2 | 3 | import android.annotation.SuppressLint 4 | import androidx.compose.foundation.layout.Spacer 5 | import androidx.compose.runtime.Composable 6 | import androidx.compose.ui.Modifier 7 | import androidx.compose.ui.unit.dp 8 | import dev.codepur.velocityx.VxWidgetBuilder 9 | import dev.codepur.velocityx.mixin.IVxModifierMixin 10 | import dev.codepur.velocityx.mixin.VxModifierMixin 11 | 12 | open class VxSpacerAddOn( 13 | modifierMixin: IVxModifierMixin = VxModifierMixin() 14 | ) : 15 | IVxModifierMixin by modifierMixin 16 | 17 | class VxSpacer : VxWidgetBuilder, VxSpacerAddOn() { 18 | 19 | init { 20 | setChildForModifier(this) 21 | 22 | } 23 | 24 | @SuppressLint("ComposableNaming") 25 | @Composable 26 | override fun make() { 27 | val currentModifier = velocityModifier ?: Modifier 28 | return Spacer(modifier = currentModifier) 29 | } 30 | 31 | 32 | } 33 | 34 | @Composable 35 | fun WidthBox(width: Number) { 36 | VxSpacer().forcedWidth(width.toDouble().dp).make() 37 | } 38 | 39 | @Composable 40 | fun WidthPCTBox(width: Number) { 41 | VxSpacer().wPCT(width.toDouble()).make() 42 | } 43 | 44 | @Composable 45 | fun HeightBox(height: Number) { 46 | VxSpacer().forcedHeight(height.toDouble().dp).make() 47 | } 48 | 49 | @Composable 50 | fun HeightPCTBox(height: Number) { 51 | VxSpacer().hPCT(height.toDouble()).make() 52 | } 53 | 54 | @Composable 55 | fun SquareBox(size: Number) { 56 | VxSpacer().forcedWidth(size.toDouble().dp).forcedHeight(size.toDouble().dp).make() 57 | } 58 | 59 | 60 | -------------------------------------------------------------------------------- /VelocityX/src/main/java/dev/codepur/velocityx/compose/VxText.kt: -------------------------------------------------------------------------------- 1 | package dev.codepur.velocityx.compose 2 | 3 | import android.annotation.SuppressLint 4 | import androidx.compose.material3.LocalTextStyle 5 | import androidx.compose.material3.MaterialTheme 6 | import androidx.compose.material3.Text 7 | import androidx.compose.runtime.Composable 8 | import androidx.compose.ui.Modifier 9 | import androidx.compose.ui.text.TextStyle 10 | import androidx.compose.ui.text.font.FontFamily 11 | import androidx.compose.ui.text.font.FontStyle 12 | import androidx.compose.ui.text.font.FontWeight 13 | import androidx.compose.ui.text.style.TextAlign 14 | import androidx.compose.ui.text.style.TextDecoration 15 | import androidx.compose.ui.text.style.TextOverflow 16 | import androidx.compose.ui.unit.sp 17 | import dev.codepur.velocityx.VxWidgetBuilder 18 | import dev.codepur.velocityx.mixin.IVxColorMixin 19 | import dev.codepur.velocityx.mixin.IVxModifierMixin 20 | import dev.codepur.velocityx.mixin.VxColorMixin 21 | import dev.codepur.velocityx.mixin.VxModifierMixin 22 | 23 | 24 | open class VxTextAddOn( 25 | colorMixin: IVxColorMixin = VxColorMixin(), 26 | modifierMixin: IVxModifierMixin = VxModifierMixin() 27 | ) : 28 | IVxColorMixin by colorMixin, IVxModifierMixin by modifierMixin 29 | 30 | class VxText(val text: String) : VxWidgetBuilder, VxTextAddOn() { 31 | 32 | init { 33 | setChildToColor(this) 34 | setChildForModifier(this) 35 | } 36 | 37 | private var _text: String = text 38 | private var _fontFamily: FontFamily? = null 39 | private var _scaleFactor: Double = 1.0 40 | private var _fontSize: Double? = null 41 | private var _letterSpacing: Double? = null 42 | private var _lineHeight: Double? = null 43 | private var _wordSpacing: Double? = null 44 | private var _maxLines: Int? = null 45 | private var _fontWeight: FontWeight? = null 46 | private var _textAlign: TextAlign? = null 47 | private var _overflow: TextOverflow? = null 48 | private var _fontStyle: FontStyle? = null 49 | private var _softWrap: Boolean = true 50 | private var _textStyle: TextStyle? = null 51 | private var _themedStyle: TextStyle? = null 52 | private var _textDecoration: TextDecoration? = null 53 | 54 | 55 | /// The text to display. 56 | /// 57 | /// This will be null if a [textSpan] is provided instead. 58 | fun text(text: String): VxText { 59 | _text = text 60 | return this 61 | } 62 | 63 | 64 | fun maxLines(lines: Int): VxText { 65 | _maxLines = lines 66 | return this 67 | } 68 | 69 | /// Sets [textScaleFactor] to extra small i.e. 0.75 70 | val xs: VxText 71 | get() = fontSizedText(child = this, scaleFactor = 0.75) 72 | 73 | /// Sets [textScaleFactor] to small i.e. 0.875 74 | val sm: VxText 75 | get() = fontSizedText(child = this, scaleFactor = 0.875) 76 | 77 | /// Sets [textScaleFactor] to base i.e. 1 or default 78 | val base: VxText 79 | get() = fontSizedText(child = this, scaleFactor = 1.0) 80 | 81 | /// Sets [textScaleFactor] to large i.e. 1.125 82 | val lg: VxText 83 | get() = fontSizedText(child = this, scaleFactor = 1.125) 84 | 85 | /// Sets [textScaleFactor] to extra large i.e. 1.25 86 | val xl: VxText 87 | get() = fontSizedText(child = this, scaleFactor = 1.25) 88 | 89 | /// Sets [textScaleFactor] to twice extra large i.e. 1.5 90 | val xl2: VxText 91 | get() = fontSizedText(child = this, scaleFactor = 1.5) 92 | 93 | /// Sets [textScaleFactor] to thrice large i.e. 1.875 94 | val xl3: VxText 95 | get() = fontSizedText(child = this, scaleFactor = 1.875) 96 | 97 | /// Sets [textScaleFactor] to four times extra large i.e. 2.25 98 | val xl4: VxText 99 | get() = fontSizedText(child = this, scaleFactor = 2.25) 100 | 101 | /// Sets [textScaleFactor] to five times extra large i.e. 3 102 | val xl5: VxText 103 | get() = fontSizedText(child = this, scaleFactor = 3.0) 104 | 105 | /// Sets [textScaleFactor] to six times extra large i.e. 4 106 | val xl6: VxText 107 | get() = fontSizedText(child = this, scaleFactor = 4.0) 108 | 109 | 110 | /// Sets [textScaleFactor] to custom value 111 | fun scale(value: Double): VxText = 112 | fontSizedText(child = this, scaleFactor = value) 113 | 114 | /// To set fontSize of the text using [size] 115 | fun size(size: Double?): VxText { 116 | _fontSize = size 117 | return this 118 | } 119 | 120 | private fun fontSizedText( 121 | scaleFactor: Double, child: VxText 122 | ): VxText { 123 | _fontSize = (_fontSize ?: 14.0) * scaleFactor 124 | _scaleFactor = scaleFactor 125 | return child 126 | } 127 | 128 | // Give custom text alignment 129 | fun align(align: TextAlign): VxText { 130 | _textAlign = align 131 | return this 132 | } 133 | 134 | /// How the text should be aligned horizontally. 135 | /// 136 | /// To align text in [center] 137 | val center: VxText 138 | get() { 139 | _textAlign = TextAlign.Center 140 | return this 141 | } 142 | 143 | /// To align text in [start] 144 | val start: VxText 145 | get() { 146 | _textAlign = TextAlign.Start 147 | return this 148 | } 149 | 150 | /// To align text in [end] 151 | val end: VxText 152 | get() { 153 | _textAlign = TextAlign.End 154 | return this 155 | } 156 | 157 | /// To align text as [justify] 158 | val justify: VxText 159 | get() { 160 | _textAlign = TextAlign.Justify 161 | return this 162 | } 163 | 164 | /// Can be used to set overflow of a text. 165 | /// How visual overflow should be handled. 166 | fun overflow(overflow: TextOverflow): VxText { 167 | _overflow = overflow 168 | return this 169 | } 170 | 171 | /// To overflow text as [clip] 172 | val clip: VxText 173 | get() { 174 | _overflow = TextOverflow.Clip 175 | return this 176 | } 177 | 178 | /// To overflow text as [ellipsis] 179 | val ellipsis: VxText 180 | get() { 181 | _overflow = TextOverflow.Ellipsis 182 | return this 183 | } 184 | 185 | /// To overflow text as [visible] 186 | val visible: VxText 187 | get() { 188 | _overflow = TextOverflow.Visible 189 | return this 190 | } 191 | 192 | /// Set [FontWeight] for the text 193 | fun fontWeight(weight: FontWeight): VxText { 194 | _fontWeight = weight 195 | return this 196 | } 197 | 198 | /// Sets [FontWeight] to [FontWeight.w100] 199 | val hairLine: VxText 200 | get() = fontWeightedText(weight = FontWeight.W100) 201 | 202 | /// Sets [FontWeight] to [FontWeight.w200] 203 | val thin: VxText 204 | get() = fontWeightedText(weight = FontWeight.W200) 205 | 206 | /// Sets [FontWeight] to [FontWeight.w300] 207 | val light: VxText 208 | get() = fontWeightedText(weight = FontWeight.W300) 209 | 210 | /// Sets [FontWeight] to [FontWeight.w400] 211 | val normal: VxText 212 | get() = fontWeightedText(weight = FontWeight.W400) 213 | 214 | /// Sets [FontWeight] to [FontWeight.w500] 215 | val medium: VxText 216 | get() = fontWeightedText(weight = FontWeight.W500) 217 | 218 | /// Sets [FontWeight] to [FontWeight.w600] 219 | val semiBold: VxText 220 | get() = fontWeightedText(weight = FontWeight.W600) 221 | 222 | /// Sets [FontWeight] to [FontWeight.w700] 223 | val bold: VxText 224 | get() = fontWeightedText(weight = FontWeight.W700) 225 | 226 | /// Sets [FontWeight] to [FontWeight.w800] 227 | val extraBold: VxText 228 | get() = fontWeightedText(weight = FontWeight.W800) 229 | 230 | /// Sets [FontWeight] to [FontWeight.w900] 231 | val extraBlack: VxText 232 | get() = fontWeightedText(weight = FontWeight.W900) 233 | 234 | private fun fontWeightedText(weight: FontWeight): VxText { 235 | _fontWeight = weight 236 | return this 237 | } 238 | 239 | /// Sets [letterSpacing] to -3.0 240 | val tightest: VxText 241 | get() = letterSpacing(-3.0) 242 | 243 | /// Sets [letterSpacing] to -2.0 244 | val tighter: VxText 245 | get() = letterSpacing(-2.0) 246 | 247 | /// Sets [letterSpacing] to -1.0 248 | val tight: VxText 249 | get() = letterSpacing(-1.0) 250 | 251 | /// Sets [letterSpacing] to 1.0 252 | val wide: VxText 253 | get() = letterSpacing(1.0) 254 | 255 | /// Sets [letterSpacing] to 2.0 256 | val wider: VxText 257 | get() = letterSpacing(2.0) 258 | 259 | /// Sets [letterSpacing] to 3.0 260 | val widest: VxText 261 | get() = letterSpacing(3.0) 262 | 263 | fun letterSpacing(spacing: Double): VxText { 264 | _letterSpacing = spacing 265 | return this 266 | } 267 | 268 | /// Sets [FontStyle] to [FontStyle.italic] 269 | val italic: VxText 270 | get() { 271 | _fontStyle = FontStyle.Italic 272 | return this 273 | } 274 | 275 | /// Sets [lineHeight] to 0.75 276 | val heightTight: VxText 277 | get() = lineHeight(0.75) 278 | 279 | /// Sets [lineHeight] to 0.875 280 | val heightSnug: VxText 281 | get() = lineHeight(0.875) 282 | 283 | /// Sets [lineHeight] to 1.25 284 | val heightRelaxed: VxText 285 | get() = lineHeight(1.25) 286 | 287 | /// Sets [lineHeight] to 1.5 288 | val heightLoose: VxText 289 | get() = lineHeight(1.5) 290 | 291 | /// Sets custom [lineHeight] with [val] 292 | fun lineHeight(height: Double): VxText { 293 | _lineHeight = height 294 | return this 295 | } 296 | 297 | /// Set [fontFamily] for the text 298 | fun fontFamily(family: FontFamily): VxText { 299 | _fontFamily = family 300 | return this 301 | } 302 | 303 | /// Whether the text should break at soft line breaks. 304 | /// 305 | /// If false, the glyphs in the text will be positioned as if there was 306 | /// unlimited horizontal space. 307 | fun softWrap(wrapValue: Boolean): VxText { 308 | _softWrap = wrapValue 309 | return this 310 | } 311 | 312 | /// Use textStyle to provide custom or any theme style. 313 | /// 314 | /// If the style's 'inherit' property is true, the style will be merged with 315 | /// the closest enclosing [DefaultTextStyle]. Otherwise, the style will 316 | /// replace the closest enclosing [DefaultTextStyle]. 317 | fun textStyle(style: TextStyle): VxText { 318 | _textStyle = style 319 | return this 320 | } 321 | 322 | /// Sets [TextTheme] headline small 323 | @Composable 324 | fun headlineSmall(): VxText { 325 | _themedStyle = MaterialTheme.typography.headlineSmall 326 | return this 327 | } 328 | 329 | /// Sets [TextTheme] headline medium 330 | @Composable 331 | fun headlineMedium(): VxText { 332 | _themedStyle = MaterialTheme.typography.headlineMedium 333 | return this 334 | } 335 | 336 | /// Sets [TextTheme] headline large 337 | @Composable 338 | fun headlineLarge(): VxText { 339 | _themedStyle = MaterialTheme.typography.headlineLarge 340 | return this 341 | } 342 | 343 | /// Sets [TextTheme] title small 344 | @Composable 345 | fun titleSmall(): VxText { 346 | _themedStyle = MaterialTheme.typography.titleSmall 347 | return this 348 | } 349 | 350 | /// Sets [TextTheme] title medium 351 | @Composable 352 | fun titleMedium(): VxText { 353 | _themedStyle = MaterialTheme.typography.titleMedium 354 | return this 355 | } 356 | 357 | /// Sets [TextTheme] title large 358 | @Composable 359 | fun titleLarge(): VxText { 360 | _themedStyle = MaterialTheme.typography.titleLarge 361 | return this 362 | } 363 | 364 | /// Sets [TextTheme] body small 365 | @Composable 366 | fun bodySmall(): VxText { 367 | _themedStyle = MaterialTheme.typography.bodySmall 368 | return this 369 | } 370 | 371 | /// Sets [TextTheme] body medium 372 | @Composable 373 | fun bodyMedium(): VxText { 374 | _themedStyle = MaterialTheme.typography.bodyMedium 375 | return this 376 | } 377 | 378 | /// Sets [TextTheme] body large 379 | @Composable 380 | fun bodyLarge(): VxText { 381 | _themedStyle = MaterialTheme.typography.bodyLarge 382 | return this 383 | } 384 | 385 | /// Sets [TextTheme] display small 386 | @Composable 387 | fun displaySmall(): VxText { 388 | _themedStyle = MaterialTheme.typography.displaySmall 389 | return this 390 | } 391 | 392 | /// Sets [TextTheme] display medium 393 | @Composable 394 | fun displayMedium(): VxText { 395 | _themedStyle = MaterialTheme.typography.displayMedium 396 | return this 397 | } 398 | 399 | /// Sets [TextTheme] display large 400 | @Composable 401 | fun displayLarge(): VxText { 402 | _themedStyle = MaterialTheme.typography.displayLarge 403 | return this 404 | } 405 | 406 | /// Sets [TextTheme] label small 407 | @Composable 408 | fun labelSmall(): VxText { 409 | _themedStyle = MaterialTheme.typography.labelSmall 410 | return this 411 | } 412 | 413 | /// Sets [TextTheme] label medium 414 | @Composable 415 | fun labelMedium(): VxText { 416 | _themedStyle = MaterialTheme.typography.labelMedium 417 | return this 418 | } 419 | 420 | /// Sets [TextTheme] label large 421 | @Composable 422 | fun labelLarge(): VxText { 423 | _themedStyle = MaterialTheme.typography.labelLarge 424 | return this 425 | } 426 | 427 | /// Sets [TextDecoration] as [TextDecoration.underline] 428 | val underline 429 | get() = decoration(TextDecoration.Underline) 430 | 431 | /// Sets [TextDecoration] as [TextDecoration.lineThrough] 432 | val lineThrough 433 | get() = decoration(TextDecoration.LineThrough) 434 | 435 | /// Sets [TextDecoration] as [TextDecoration.None] 436 | val noneDecoration 437 | get() = decoration(TextDecoration.None) 438 | 439 | ///Sets TextDecoration 440 | fun decoration(decorator: TextDecoration): VxText { 441 | _textDecoration = decorator 442 | return this 443 | } 444 | 445 | /// Converts the text to fully uppercase. 446 | val uppercase: VxText 447 | get() = setText(_text.uppercase()) 448 | 449 | /// Converts the text to fully lowercase. 450 | val lowercase: VxText 451 | get() = setText(_text.lowercase()) 452 | 453 | 454 | ///Modifies Text 455 | private fun setText(newText: String): VxText { 456 | _text = newText 457 | return this 458 | } 459 | 460 | @SuppressLint("ComposableNaming") 461 | @Composable 462 | override fun make() { 463 | var currentModifier = velocityModifier ?: Modifier 464 | val currentContext = LocalTextStyle.current 465 | var newStyle = _themedStyle ?: _textStyle ?: currentContext 466 | val ts = TextStyle( 467 | color = velocityColor ?: newStyle.color, 468 | fontSize = _fontSize?.sp ?: newStyle.fontSize, 469 | fontWeight = _fontWeight ?: newStyle.fontWeight, 470 | textAlign = _textAlign ?: newStyle.textAlign, 471 | letterSpacing = _letterSpacing?.sp ?: newStyle.letterSpacing, 472 | fontStyle = _fontStyle ?: newStyle.fontStyle, 473 | lineHeight = _lineHeight?.sp ?: newStyle.lineHeight, 474 | fontFamily = _fontFamily ?: newStyle.fontFamily, 475 | textDecoration = _textDecoration ?: newStyle.textDecoration, 476 | ) 477 | newStyle = _themedStyle?.merge(ts) ?: _textStyle?.merge(ts) ?: ts 478 | 479 | Text( 480 | text = _text, 481 | color = newStyle.color, 482 | fontSize = newStyle.fontSize, 483 | fontWeight = newStyle.fontWeight, 484 | textAlign = newStyle.textAlign, 485 | maxLines = _maxLines ?: Int.MAX_VALUE, 486 | letterSpacing = newStyle.letterSpacing, 487 | fontStyle = newStyle.fontStyle, 488 | overflow = _overflow ?: TextOverflow.Clip, 489 | lineHeight = newStyle.lineHeight, 490 | softWrap = _softWrap, 491 | fontFamily = newStyle.fontFamily, 492 | style = newStyle, 493 | textDecoration = newStyle.textDecoration, 494 | modifier = currentModifier, 495 | 496 | ) 497 | } 498 | 499 | 500 | } 501 | 502 | val String.text get() = VxText(text = this) 503 | 504 | -------------------------------------------------------------------------------- /VelocityX/src/main/java/dev/codepur/velocityx/compose/VxWidgets.kt: -------------------------------------------------------------------------------- 1 | package dev.codepur.velocityx.compose 2 | 3 | -------------------------------------------------------------------------------- /VelocityX/src/main/java/dev/codepur/velocityx/extensions/Language.kt: -------------------------------------------------------------------------------- 1 | package dev.codepur.velocityx.extensions 2 | 3 | /// flag for short form e.g(1 min) | long form e.g(1 minute ago) 4 | abstract class Language(val shortForm: Boolean) { 5 | abstract fun prefixAgo(): String 6 | 7 | abstract fun prefixFromNow(): String 8 | 9 | abstract fun suffixAgo(): String 10 | abstract fun suffixFromNow(): String 11 | 12 | abstract fun lessThanOneMinute(seconds: Int): String 13 | abstract fun aboutAMinute(minutes: Int): String 14 | abstract fun minutes(minutes: Int): String 15 | 16 | abstract fun aboutAnHour(minutes: Int): String 17 | abstract fun hours(hours: Int): String 18 | 19 | abstract fun aDay(hours: Int): String 20 | abstract fun days(days: Int): String 21 | 22 | abstract fun aboutAMonth(days: Int): String 23 | abstract fun months(months: Int): String 24 | 25 | abstract fun aboutAYear(year: Int): String 26 | abstract fun years(years: Int): String 27 | 28 | abstract fun delimiter(): String 29 | } 30 | 31 | /// To use [English] language for timeAgo. More languages can be added in the future. 32 | class English(shortForm: Boolean = false) : Language(shortForm) { 33 | 34 | override fun prefixAgo(): String = "" 35 | 36 | override fun prefixFromNow(): String = "" 37 | 38 | override fun suffixAgo(): String = if (shortForm) "" else "ago" 39 | 40 | override fun suffixFromNow(): String = if (shortForm) "" else "from now" 41 | 42 | override fun lessThanOneMinute(seconds: Int): String = if (shortForm) "now" else "a moment" 43 | 44 | override fun aboutAMinute(minutes: Int): String = if (shortForm) "1 min" else "a minute" 45 | 46 | override fun minutes(minutes: Int): String = 47 | if (shortForm) "$minutes min" else "$minutes minutes" 48 | 49 | override fun aboutAnHour(minutes: Int): String = if (shortForm) "~1 h" else "about an hour" 50 | 51 | override fun hours(hours: Int): String = if (shortForm) "$hours h" else "$hours hours" 52 | 53 | override fun aDay(hours: Int): String = if (shortForm) "~1 d" else "a day" 54 | 55 | override fun days(days: Int): String = if (shortForm) "$days d" else "$days days" 56 | 57 | override fun aboutAMonth(days: Int): String = if (shortForm) "~1 mo" else "about a month" 58 | 59 | override fun months(months: Int): String = if (shortForm) "$months mo" else "$months months" 60 | 61 | override fun aboutAYear(year: Int): String = if (shortForm) "~1 yr" else "about a year" 62 | 63 | override fun years(years: Int): String = if (shortForm) "$years yr" else "$years years" 64 | 65 | override fun delimiter(): String = " " 66 | } -------------------------------------------------------------------------------- /VelocityX/src/main/java/dev/codepur/velocityx/extensions/date_time_ext.kt: -------------------------------------------------------------------------------- 1 | package dev.codepur.velocityx.extensions 2 | 3 | import android.os.Build 4 | import androidx.annotation.RequiresApi 5 | import java.time.LocalDateTime 6 | import java.time.ZoneId 7 | import kotlin.math.absoluteValue 8 | 9 | @RequiresApi(Build.VERSION_CODES.O) 10 | fun LocalDateTime.timeAgo( 11 | clock: LocalDateTime = LocalDateTime.now(), 12 | enableFromNow: Boolean = false, 13 | useShortForm: Boolean = false 14 | ): String { 15 | val mIsFromNowEnabled: Boolean = enableFromNow 16 | 17 | val mLanguage: Language = English(useShortForm) 18 | 19 | val mClock: LocalDateTime = clock 20 | 21 | var deltaTime: Long = mClock.atZone(ZoneId.systemDefault()).toInstant() 22 | .toEpochMilli() - this.atZone(ZoneId.systemDefault()).toInstant().toEpochMilli() 23 | 24 | val pfx: String 25 | 26 | val sfx: String 27 | 28 | if (mIsFromNowEnabled && deltaTime < 0) { 29 | deltaTime = if (this.isBefore(mClock)) deltaTime else deltaTime.absoluteValue 30 | pfx = mLanguage.prefixFromNow() 31 | sfx = mLanguage.suffixFromNow() 32 | } else { 33 | pfx = mLanguage.prefixAgo() 34 | sfx = mLanguage.suffixAgo() 35 | } 36 | 37 | val seconds: Long = deltaTime / 1000 38 | val minutes: Long = seconds / 60 39 | val hours: Long = minutes / 60 40 | val days: Long = hours / 24 41 | val months: Long = days / 30 42 | val years: Long = days / 365 43 | 44 | val res: String 45 | 46 | if (seconds < 45) { 47 | res = mLanguage.lessThanOneMinute(seconds.toInt()) 48 | } else if (seconds < 90) { 49 | res = mLanguage.aboutAMinute(minutes.toInt()) 50 | } else if (minutes < 45) { 51 | res = mLanguage.minutes(minutes.toInt()) 52 | } else if (minutes < 90) { 53 | res = mLanguage.aboutAnHour(minutes.toInt()) 54 | } else if (hours < 24) { 55 | res = mLanguage.hours(hours.toInt()) 56 | } else if (hours < 48) { 57 | res = mLanguage.aDay(hours.toInt()) 58 | } else if (days < 30) { 59 | res = mLanguage.days(days.toInt()) 60 | } else if (days < 60) { 61 | res = mLanguage.aboutAMonth(days.toInt()) 62 | } else if (days < 365) { 63 | res = mLanguage.months(months.toInt()) 64 | } else if (years < 2) { 65 | res = mLanguage.aboutAYear(months.toInt()) 66 | } else { 67 | res = mLanguage.years(years.toInt()) 68 | } 69 | return listOf(pfx, res, sfx).joinToString(mLanguage.delimiter()) 70 | } -------------------------------------------------------------------------------- /VelocityX/src/main/java/dev/codepur/velocityx/mixin/VxAlignmentMixin.kt: -------------------------------------------------------------------------------- 1 | package dev.codepur.velocityx.mixin 2 | 3 | import androidx.compose.ui.Alignment 4 | 5 | interface IVxAlignmentMixin { 6 | 7 | var velocityAlignment: Alignment? 8 | 9 | val alignTopCenter: T 10 | get() = alignment(alignment = Alignment.TopCenter) 11 | 12 | val alignTopLeft: T 13 | get() = alignment(alignment = Alignment.TopStart) 14 | 15 | val alignTopRight: T 16 | get() = alignment(alignment = Alignment.TopEnd) 17 | 18 | val alignCenter: T 19 | get() = alignment(alignment = Alignment.Center) 20 | 21 | val alignCenterLeft: T 22 | get() = alignment(alignment = Alignment.CenterStart) 23 | 24 | val alignCenterRight: T 25 | get() = alignment(alignment = Alignment.CenterEnd) 26 | 27 | val alignBottomCenter: T 28 | get() = alignment(alignment = Alignment.BottomCenter) 29 | 30 | val alignBottomLeft: T 31 | get() = alignment(alignment = Alignment.BottomStart) 32 | 33 | val alignBottomRight: T 34 | get() = alignment(alignment = Alignment.BottomEnd) 35 | 36 | fun setChildForAlignment(child: T) 37 | 38 | fun alignment(alignment: Alignment): T 39 | 40 | } 41 | 42 | class VxAlignmentMixin : IVxAlignmentMixin { 43 | private var _child: T? = null 44 | 45 | override var velocityAlignment: Alignment? = null 46 | 47 | override fun setChildForAlignment(child: T) { 48 | _child = child 49 | } 50 | 51 | override fun alignment(alignment: Alignment): T { 52 | velocityAlignment = alignment 53 | return _child!! 54 | 55 | } 56 | 57 | 58 | } 59 | -------------------------------------------------------------------------------- /VelocityX/src/main/java/dev/codepur/velocityx/mixin/VxColorMixin.kt: -------------------------------------------------------------------------------- 1 | package dev.codepur.velocityx.mixin 2 | 3 | import androidx.compose.ui.graphics.Color 4 | import dev.codepur.velocityx.Vx 5 | 6 | 7 | interface IVxColorMixin { 8 | var velocityColor: Color? 9 | 10 | fun color(color: Color): T 11 | 12 | fun hexColor(colorHex: String): T 13 | 14 | fun setChildToColor(child: T) 15 | 16 | ///Transparent 17 | val transparent: T 18 | get() = color(color = Color.Transparent) 19 | 20 | val white: T 21 | get() = color(color = Color.White) 22 | 23 | ///Gray 24 | val gray50: T 25 | get() = color(color = Vx.gray50) 26 | val gray100: T 27 | get() = color(color = Vx.gray100) 28 | val gray200: T 29 | get() = color(color = Vx.gray200) 30 | val gray300: T 31 | get() = color(color = Vx.gray300) 32 | val gray400: T 33 | get() = color(color = Vx.gray400) 34 | val gray500: T 35 | get() = color(color = Vx.gray500) 36 | val gray600: T 37 | get() = color(color = Vx.gray600) 38 | val gray700: T 39 | get() = color(color = Vx.gray700) 40 | val gray800: T 41 | get() = color(color = Vx.gray800) 42 | val gray900: T 43 | get() = color(color = Vx.gray900) 44 | 45 | ///Slate 46 | val slate50: T 47 | get() = color(color = Vx.slate50) 48 | val slate100: T 49 | get() = color(color = Vx.slate100) 50 | val slate200: T 51 | get() = color(color = Vx.slate200) 52 | val slate300: T 53 | get() = color(color = Vx.slate300) 54 | val slate400: T 55 | get() = color(color = Vx.slate400) 56 | val slate500: T 57 | get() = color(color = Vx.slate500) 58 | val slate600: T 59 | get() = color(color = Vx.slate600) 60 | val slate700: T 61 | get() = color(color = Vx.slate700) 62 | val slate800: T 63 | get() = color(color = Vx.slate800) 64 | val slate900: T 65 | get() = color(color = Vx.slate900) 66 | 67 | ///Zinc 68 | val zinc50: T 69 | get() = color(color = Vx.zinc50) 70 | val zinc100: T 71 | get() = color(color = Vx.zinc100) 72 | val zinc200: T 73 | get() = color(color = Vx.zinc200) 74 | val zinc300: T 75 | get() = color(color = Vx.zinc300) 76 | val zinc400: T 77 | get() = color(color = Vx.zinc400) 78 | val zinc500: T 79 | get() = color(color = Vx.zinc500) 80 | val zinc600: T 81 | get() = color(color = Vx.zinc600) 82 | val zinc700: T 83 | get() = color(color = Vx.zinc700) 84 | val zinc800: T 85 | get() = color(color = Vx.zinc800) 86 | val zinc900: T 87 | get() = color(color = Vx.zinc900) 88 | 89 | ///Neutral 90 | val neutral50: T 91 | get() = color(color = Vx.neutral50) 92 | val neutral100: T 93 | get() = color(color = Vx.neutral100) 94 | val neutral200: T 95 | get() = color(color = Vx.neutral200) 96 | val neutral300: T 97 | get() = color(color = Vx.neutral300) 98 | val neutral400: T 99 | get() = color(color = Vx.neutral400) 100 | val neutral500: T 101 | get() = color(color = Vx.neutral500) 102 | val neutral600: T 103 | get() = color(color = Vx.neutral600) 104 | val neutral700: T 105 | get() = color(color = Vx.neutral700) 106 | val neutral800: T 107 | get() = color(color = Vx.neutral800) 108 | val neutral900: T 109 | get() = color(color = Vx.neutral900) 110 | 111 | ///Stone 112 | val stone50: T 113 | get() = color(color = Vx.stone50) 114 | val stone100: T 115 | get() = color(color = Vx.stone100) 116 | val stone200: T 117 | get() = color(color = Vx.stone200) 118 | val stone300: T 119 | get() = color(color = Vx.stone300) 120 | val stone400: T 121 | get() = color(color = Vx.stone400) 122 | val stone500: T 123 | get() = color(color = Vx.stone500) 124 | val stone600: T 125 | get() = color(color = Vx.stone600) 126 | val stone700: T 127 | get() = color(color = Vx.stone700) 128 | val stone800: T 129 | get() = color(color = Vx.stone800) 130 | val stone900: T 131 | get() = color(color = Vx.stone900) 132 | 133 | ///Red 134 | val red50: T 135 | get() = color(color = Vx.red50) 136 | val red100: T 137 | get() = color(color = Vx.red100) 138 | val red200: T 139 | get() = color(color = Vx.red200) 140 | val red300: T 141 | get() = color(color = Vx.red300) 142 | val red400: T 143 | get() = color(color = Vx.red400) 144 | val red500: T 145 | get() = color(color = Vx.red500) 146 | val red600: T 147 | get() = color(color = Vx.red600) 148 | val red700: T 149 | get() = color(color = Vx.red700) 150 | val red800: T 151 | get() = color(color = Vx.red800) 152 | val red900: T 153 | get() = color(color = Vx.red900) 154 | 155 | ///Orange 156 | val orange50: T 157 | get() = color(color = Vx.orange50) 158 | val orange100: T 159 | get() = color(color = Vx.orange100) 160 | val orange200: T 161 | get() = color(color = Vx.orange200) 162 | val orange300: T 163 | get() = color(color = Vx.orange300) 164 | val orange400: T 165 | get() = color(color = Vx.orange400) 166 | val orange500: T 167 | get() = color(color = Vx.orange500) 168 | val orange600: T 169 | get() = color(color = Vx.orange600) 170 | val orange700: T 171 | get() = color(color = Vx.orange700) 172 | val orange800: T 173 | get() = color(color = Vx.orange800) 174 | val orange900: T 175 | get() = color(color = Vx.orange900) 176 | 177 | ///Amber 178 | val amber50: T 179 | get() = color(color = Vx.amber50) 180 | val amber100: T 181 | get() = color(color = Vx.amber100) 182 | val amber200: T 183 | get() = color(color = Vx.amber200) 184 | val amber300: T 185 | get() = color(color = Vx.amber300) 186 | val amber400: T 187 | get() = color(color = Vx.amber400) 188 | val amber500: T 189 | get() = color(color = Vx.amber500) 190 | val amber600: T 191 | get() = color(color = Vx.amber600) 192 | val amber700: T 193 | get() = color(color = Vx.amber700) 194 | val amber800: T 195 | get() = color(color = Vx.amber800) 196 | val amber900: T 197 | get() = color(color = Vx.amber900) 198 | 199 | ///Yellow 200 | val yellow50: T 201 | get() = color(color = Vx.yellow50) 202 | val yellow100: T 203 | get() = color(color = Vx.yellow100) 204 | val yellow200: T 205 | get() = color(color = Vx.yellow200) 206 | val yellow300: T 207 | get() = color(color = Vx.yellow300) 208 | val yellow400: T 209 | get() = color(color = Vx.yellow400) 210 | val yellow500: T 211 | get() = color(color = Vx.yellow500) 212 | val yellow600: T 213 | get() = color(color = Vx.yellow600) 214 | val yellow700: T 215 | get() = color(color = Vx.yellow700) 216 | val yellow800: T 217 | get() = color(color = Vx.yellow800) 218 | val yellow900: T 219 | get() = color(color = Vx.yellow900) 220 | 221 | ///Lime 222 | val lime50: T 223 | get() = color(color = Vx.lime50) 224 | val lime100: T 225 | get() = color(color = Vx.lime100) 226 | val lime200: T 227 | get() = color(color = Vx.lime200) 228 | val lime300: T 229 | get() = color(color = Vx.lime300) 230 | val lime400: T 231 | get() = color(color = Vx.lime400) 232 | val lime500: T 233 | get() = color(color = Vx.lime500) 234 | val lime600: T 235 | get() = color(color = Vx.lime600) 236 | val lime700: T 237 | get() = color(color = Vx.lime700) 238 | val lime800: T 239 | get() = color(color = Vx.lime800) 240 | val lime900: T 241 | get() = color(color = Vx.lime900) 242 | 243 | ///Green 244 | val green50: T 245 | get() = color(color = Vx.green50) 246 | val green100: T 247 | get() = color(color = Vx.green100) 248 | val green200: T 249 | get() = color(color = Vx.green200) 250 | val green300: T 251 | get() = color(color = Vx.green300) 252 | val green400: T 253 | get() = color(color = Vx.green400) 254 | val green500: T 255 | get() = color(color = Vx.green500) 256 | val green600: T 257 | get() = color(color = Vx.green600) 258 | val green700: T 259 | get() = color(color = Vx.green700) 260 | val green800: T 261 | get() = color(color = Vx.green800) 262 | val green900: T 263 | get() = color(color = Vx.green900) 264 | 265 | ///Emerald 266 | val emerald50: T 267 | get() = color(color = Vx.emerald50) 268 | val emerald100: T 269 | get() = color(color = Vx.emerald100) 270 | val emerald200: T 271 | get() = color(color = Vx.emerald200) 272 | val emerald300: T 273 | get() = color(color = Vx.emerald300) 274 | val emerald400: T 275 | get() = color(color = Vx.emerald400) 276 | val emerald500: T 277 | get() = color(color = Vx.emerald500) 278 | val emerald600: T 279 | get() = color(color = Vx.emerald600) 280 | val emerald700: T 281 | get() = color(color = Vx.emerald700) 282 | val emerald800: T 283 | get() = color(color = Vx.emerald800) 284 | val emerald900: T 285 | get() = color(color = Vx.emerald900) 286 | 287 | ///teal 288 | val teal50: T 289 | get() = color(color = Vx.teal50) 290 | val teal100: T 291 | get() = color(color = Vx.teal100) 292 | val teal200: T 293 | get() = color(color = Vx.teal200) 294 | val teal300: T 295 | get() = color(color = Vx.teal300) 296 | val teal400: T 297 | get() = color(color = Vx.teal400) 298 | val teal500: T 299 | get() = color(color = Vx.teal500) 300 | val teal600: T 301 | get() = color(color = Vx.teal600) 302 | val teal700: T 303 | get() = color(color = Vx.teal700) 304 | val teal800: T 305 | get() = color(color = Vx.teal800) 306 | val teal900: T 307 | get() = color(color = Vx.teal900) 308 | 309 | ///Cyan 310 | val cyan50: T 311 | get() = color(color = Vx.cyan50) 312 | val cyan100: T 313 | get() = color(color = Vx.cyan100) 314 | val cyan200: T 315 | get() = color(color = Vx.cyan200) 316 | val cyan300: T 317 | get() = color(color = Vx.cyan300) 318 | val cyan400: T 319 | get() = color(color = Vx.cyan400) 320 | val cyan500: T 321 | get() = color(color = Vx.cyan500) 322 | val cyan600: T 323 | get() = color(color = Vx.cyan600) 324 | val cyan700: T 325 | get() = color(color = Vx.cyan700) 326 | val cyan800: T 327 | get() = color(color = Vx.cyan800) 328 | val cyan900: T 329 | get() = color(color = Vx.cyan900) 330 | 331 | ///Sky 332 | val sky50: T 333 | get() = color(color = Vx.sky50) 334 | val sky100: T 335 | get() = color(color = Vx.sky100) 336 | val sky200: T 337 | get() = color(color = Vx.sky200) 338 | val sky300: T 339 | get() = color(color = Vx.sky300) 340 | val sky400: T 341 | get() = color(color = Vx.sky400) 342 | val sky500: T 343 | get() = color(color = Vx.sky500) 344 | val sky600: T 345 | get() = color(color = Vx.sky600) 346 | val sky700: T 347 | get() = color(color = Vx.sky700) 348 | val sky800: T 349 | get() = color(color = Vx.sky800) 350 | val sky900: T 351 | get() = color(color = Vx.sky900) 352 | 353 | ///Blue 354 | val blue50: T 355 | get() = color(color = Vx.blue50) 356 | val blue100: T 357 | get() = color(color = Vx.blue100) 358 | val blue200: T 359 | get() = color(color = Vx.blue200) 360 | val blue300: T 361 | get() = color(color = Vx.blue300) 362 | val blue400: T 363 | get() = color(color = Vx.blue400) 364 | val blue500: T 365 | get() = color(color = Vx.blue500) 366 | val blue600: T 367 | get() = color(color = Vx.blue600) 368 | val blue700: T 369 | get() = color(color = Vx.blue700) 370 | val blue800: T 371 | get() = color(color = Vx.blue800) 372 | val blue900: T 373 | get() = color(color = Vx.blue900) 374 | 375 | ///Indigo 376 | val indigo50: T 377 | get() = color(color = Vx.indigo50) 378 | val indigo100: T 379 | get() = color(color = Vx.indigo100) 380 | val indigo200: T 381 | get() = color(color = Vx.indigo200) 382 | val indigo300: T 383 | get() = color(color = Vx.indigo300) 384 | val indigo400: T 385 | get() = color(color = Vx.indigo400) 386 | val indigo500: T 387 | get() = color(color = Vx.indigo500) 388 | val indigo600: T 389 | get() = color(color = Vx.indigo600) 390 | val indigo700: T 391 | get() = color(color = Vx.indigo700) 392 | val indigo800: T 393 | get() = color(color = Vx.indigo800) 394 | val indigo900: T 395 | get() = color(color = Vx.indigo900) 396 | 397 | ///Violet 398 | val violet50: T 399 | get() = color(color = Vx.violet50) 400 | val violet100: T 401 | get() = color(color = Vx.violet100) 402 | val violet200: T 403 | get() = color(color = Vx.violet200) 404 | val violet300: T 405 | get() = color(color = Vx.violet300) 406 | val violet400: T 407 | get() = color(color = Vx.violet400) 408 | val violet500: T 409 | get() = color(color = Vx.violet500) 410 | val violet600: T 411 | get() = color(color = Vx.violet600) 412 | val violet700: T 413 | get() = color(color = Vx.violet700) 414 | val violet800: T 415 | get() = color(color = Vx.violet800) 416 | val violet900: T 417 | get() = color(color = Vx.violet900) 418 | 419 | ///Purple 420 | val purple50: T 421 | get() = color(color = Vx.purple50) 422 | val purple100: T 423 | get() = color(color = Vx.purple100) 424 | val purple200: T 425 | get() = color(color = Vx.purple200) 426 | val purple300: T 427 | get() = color(color = Vx.purple300) 428 | val purple400: T 429 | get() = color(color = Vx.purple400) 430 | val purple500: T 431 | get() = color(color = Vx.purple500) 432 | val purple600: T 433 | get() = color(color = Vx.purple600) 434 | val purple700: T 435 | get() = color(color = Vx.purple700) 436 | val purple800: T 437 | get() = color(color = Vx.purple800) 438 | val purple900: T 439 | get() = color(color = Vx.purple900) 440 | 441 | ///Fuchsia 442 | val fuchsia50: T 443 | get() = color(color = Vx.fuchsia50) 444 | val fuchsia100: T 445 | get() = color(color = Vx.fuchsia100) 446 | val fuchsia200: T 447 | get() = color(color = Vx.fuchsia200) 448 | val fuchsia300: T 449 | get() = color(color = Vx.fuchsia300) 450 | val fuchsia400: T 451 | get() = color(color = Vx.fuchsia400) 452 | val fuchsia500: T 453 | get() = color(color = Vx.fuchsia500) 454 | val fuchsia600: T 455 | get() = color(color = Vx.fuchsia600) 456 | val fuchsia700: T 457 | get() = color(color = Vx.fuchsia700) 458 | val fuchsia800: T 459 | get() = color(color = Vx.fuchsia800) 460 | val fuchsia900: T 461 | get() = color(color = Vx.fuchsia900) 462 | 463 | ///Pink 464 | val pink50: T 465 | get() = color(color = Vx.pink50) 466 | val pink100: T 467 | get() = color(color = Vx.pink100) 468 | val pink200: T 469 | get() = color(color = Vx.pink200) 470 | val pink300: T 471 | get() = color(color = Vx.pink300) 472 | val pink400: T 473 | get() = color(color = Vx.pink400) 474 | val pink500: T 475 | get() = color(color = Vx.pink500) 476 | val pink600: T 477 | get() = color(color = Vx.pink600) 478 | val pink700: T 479 | get() = color(color = Vx.pink700) 480 | val pink800: T 481 | get() = color(color = Vx.pink800) 482 | val pink900: T 483 | get() = color(color = Vx.pink900) 484 | 485 | ///Rose 486 | val rose50: T 487 | get() = color(color = Vx.rose50) 488 | val rose100: T 489 | get() = color(color = Vx.rose100) 490 | val rose200: T 491 | get() = color(color = Vx.rose200) 492 | val rose300: T 493 | get() = color(color = Vx.rose300) 494 | val rose400: T 495 | get() = color(color = Vx.rose400) 496 | val rose500: T 497 | get() = color(color = Vx.rose500) 498 | val rose600: T 499 | get() = color(color = Vx.rose600) 500 | val rose700: T 501 | get() = color(color = Vx.rose700) 502 | val rose800: T 503 | get() = color(color = Vx.rose800) 504 | val rose900: T 505 | get() = color(color = Vx.rose900) 506 | 507 | 508 | } 509 | 510 | class VxColorMixin : IVxColorMixin { 511 | private var _childToColor: T? = null 512 | override var velocityColor: Color? = null 513 | 514 | override fun setChildToColor(child: T) { 515 | _childToColor = child 516 | } 517 | 518 | /// Sets [color] of the text using Hex value 519 | override fun hexColor(colorHex: String): T { 520 | velocityColor = Vx.hexToColor(colorHex) 521 | return _childToColor!! 522 | } 523 | 524 | /// Sets [color] of the text 525 | override fun color(color: Color): T { 526 | velocityColor = color 527 | return _childToColor!! 528 | } 529 | } 530 | -------------------------------------------------------------------------------- /VelocityX/src/main/java/dev/codepur/velocityx/mixin/VxGradientMixin.kt: -------------------------------------------------------------------------------- 1 | package dev.codepur.velocityx.mixin 2 | 3 | import androidx.compose.foundation.background 4 | import androidx.compose.ui.Modifier 5 | import androidx.compose.ui.geometry.Offset 6 | import androidx.compose.ui.graphics.Brush 7 | import androidx.compose.ui.graphics.Color 8 | import androidx.compose.ui.graphics.TileMode 9 | 10 | interface IVxGradientMixin { 11 | fun linearGradient( 12 | colorStops: Array>? = null, 13 | colors: List? = null, 14 | start: Offset = Offset.Zero, 15 | end: Offset = Offset.Infinite, 16 | tileMode: TileMode = TileMode.Clamp 17 | ): T 18 | 19 | fun radialGradient( 20 | colorStops: Array>?, 21 | colors: List?, 22 | center: Offset, 23 | radius: Float, 24 | tileMode: TileMode 25 | ): T 26 | 27 | fun sweepGradient( 28 | colorStops: Array>?, 29 | colors: List?, 30 | center: Offset, 31 | ): T 32 | 33 | } 34 | 35 | class VxGradientMixin(private var vxModifierMixin: VxModifierMixin, private var _child: T?) : 36 | IVxGradientMixin { 37 | override fun linearGradient( 38 | colorStops: Array>?, 39 | colors: List?, 40 | start: Offset, 41 | end: Offset, 42 | tileMode: TileMode 43 | ): T { 44 | vxModifierMixin.velocityModifier = if (vxModifierMixin.velocityModifier != null) { 45 | if (colorStops != null) { 46 | vxModifierMixin.velocityModifier!!.background( 47 | brush = Brush.linearGradient( 48 | colorStops = colorStops, 49 | start = start, 50 | end = end, 51 | tileMode = tileMode, 52 | 53 | ) 54 | ) 55 | } else { 56 | vxModifierMixin.velocityModifier!!.background( 57 | brush = Brush.linearGradient( 58 | colors = colors!!, 59 | start = start, 60 | end = end, 61 | tileMode = tileMode 62 | 63 | ) 64 | ) 65 | } 66 | 67 | } else { 68 | if (colorStops != null) { 69 | Modifier.background( 70 | brush = Brush.linearGradient( 71 | colorStops = colorStops, 72 | start = start, 73 | end = end, 74 | tileMode = tileMode 75 | 76 | ) 77 | ) 78 | } else { 79 | Modifier.background( 80 | brush = Brush.linearGradient( 81 | colors = colors!!, 82 | start = start, 83 | end = end, 84 | tileMode = tileMode 85 | ) 86 | ) 87 | } 88 | } 89 | 90 | return _child!! 91 | } 92 | 93 | override fun radialGradient( 94 | colorStops: Array>?, 95 | colors: List?, 96 | center: Offset, 97 | radius: Float, 98 | tileMode: TileMode 99 | ): T { 100 | vxModifierMixin.velocityModifier = if (vxModifierMixin.velocityModifier != null) { 101 | if (colorStops != null) { 102 | vxModifierMixin.velocityModifier!!.background( 103 | brush = Brush.radialGradient( 104 | colorStops = colorStops, 105 | center = center, 106 | radius = radius, 107 | tileMode = tileMode 108 | 109 | ) 110 | ) 111 | } else { 112 | vxModifierMixin.velocityModifier!!.background( 113 | brush = Brush.radialGradient( 114 | colors = colors!!, radius = radius, center = center, tileMode = tileMode 115 | 116 | ) 117 | ) 118 | } 119 | 120 | } else { 121 | if (colorStops != null) { 122 | Modifier.background( 123 | brush = Brush.radialGradient( 124 | colorStops = colorStops, 125 | center = center, 126 | radius = radius, 127 | tileMode = tileMode 128 | ) 129 | ) 130 | } else { 131 | Modifier.background( 132 | brush = Brush.radialGradient( 133 | colors = colors!!, radius = radius, center = center, tileMode = tileMode 134 | ) 135 | ) 136 | } 137 | } 138 | 139 | return _child!! 140 | } 141 | 142 | override fun sweepGradient( 143 | colorStops: Array>?, 144 | colors: List?, 145 | center: Offset 146 | ): T { 147 | vxModifierMixin.velocityModifier = if (vxModifierMixin.velocityModifier != null) { 148 | if (colorStops != null) { 149 | vxModifierMixin.velocityModifier!!.background( 150 | brush = Brush.sweepGradient(colorStops = colorStops, center = center) 151 | ) 152 | } else { 153 | vxModifierMixin.velocityModifier!!.background( 154 | brush = Brush.sweepGradient(colors = colors!!, center = center) 155 | ) 156 | } 157 | 158 | } else { 159 | if (colorStops != null) { 160 | Modifier.background( 161 | brush = Brush.sweepGradient(colorStops = colorStops, center = center) 162 | ) 163 | } else { 164 | Modifier.background( 165 | brush = Brush.sweepGradient(colors = colors!!, center = center) 166 | ) 167 | } 168 | } 169 | 170 | return _child!! 171 | } 172 | 173 | } -------------------------------------------------------------------------------- /VelocityX/src/main/java/dev/codepur/velocityx/mixin/VxModifierMixin.kt: -------------------------------------------------------------------------------- 1 | package dev.codepur.velocityx.mixin 2 | 3 | import androidx.compose.foundation.* 4 | import androidx.compose.foundation.gestures.FlingBehavior 5 | import androidx.compose.foundation.layout.* 6 | import androidx.compose.foundation.shape.CircleShape 7 | import androidx.compose.foundation.shape.RoundedCornerShape 8 | import androidx.compose.runtime.Composable 9 | import androidx.compose.ui.Modifier 10 | import androidx.compose.ui.draw.clip 11 | import androidx.compose.ui.draw.shadow 12 | import androidx.compose.ui.geometry.Offset 13 | import androidx.compose.ui.graphics.* 14 | import androidx.compose.ui.platform.LocalConfiguration 15 | import androidx.compose.ui.platform.testTag 16 | import androidx.compose.ui.unit.Dp 17 | import androidx.compose.ui.unit.dp 18 | import dev.codepur.velocityx.Vx 19 | 20 | interface IVxModifierMixin : IVxPaddingMixin, IVxTransformMixin, 21 | IVxSizeMixin, IVxGradientMixin { 22 | var velocityModifier: Modifier? 23 | fun setChildForModifier(child: T) 24 | fun modifier(value: Modifier): T 25 | fun withRounded(value: Dp): T 26 | fun withShadow(value: Dp): T 27 | fun clip(shape: Shape): T 28 | fun bg(color: Color, shape: Shape = RectangleShape): T 29 | fun clickable(onClick: () -> Unit, enabled: Boolean = true): T 30 | fun testTag(tag: String): T 31 | fun border( 32 | width: Dp? = 2.dp, 33 | color: Color? = Vx.black, 34 | shape: Shape? = RectangleShape, 35 | ): T 36 | 37 | fun scrollHorizontal( 38 | state: ScrollState, 39 | enabled: Boolean = true, 40 | flingBehavior: FlingBehavior? = null, 41 | reverseScrolling: Boolean = false 42 | ): T 43 | 44 | fun scrollVertical( 45 | state: ScrollState, 46 | enabled: Boolean = true, 47 | flingBehavior: FlingBehavior? = null, 48 | reverseScrolling: Boolean = false 49 | ): T 50 | 51 | 52 | /// Rounding 53 | val roundedSm: T 54 | get() = withRounded(7.5.dp) 55 | 56 | val rounded: T 57 | get() = withRounded(15.0.dp) 58 | 59 | val roundedLg: T 60 | get() = withRounded(30.0.dp) 61 | 62 | val circle: T 63 | get() = clip(shape = CircleShape) 64 | 65 | 66 | /// Shadow 67 | val shadowXs: T 68 | get() = withShadow(1.dp) 69 | 70 | val shadowSm: T 71 | get() = withShadow(2.dp) 72 | 73 | val shadowMd: T 74 | get() = withShadow(3.dp) 75 | 76 | val shadowLg: T 77 | get() = withShadow(4.dp) 78 | 79 | val shadowXl: T 80 | get() = withShadow(6.dp) 81 | 82 | val shadow2Xl: T 83 | get() = withShadow(8.dp) 84 | val shadow3Xl: T 85 | get() = withShadow(9.dp) 86 | val shadow4Xl: T 87 | get() = withShadow(12.dp) 88 | val shadow5Xl: T 89 | get() = withShadow(16.dp) 90 | val shadowMax: T 91 | get() = withShadow(24.dp) 92 | 93 | } 94 | 95 | class VxModifierMixin : IVxModifierMixin { 96 | private var _child: T? = null 97 | override var velocityModifier: Modifier? = null 98 | private var vxTransform: IVxTransformMixin? = null 99 | private var vxGradient: IVxGradientMixin? = null 100 | 101 | override fun setChildForModifier(child: T) { 102 | _child = child 103 | vxTransform = VxTransformMixin(this, _child = child) 104 | vxGradient = VxGradientMixin(this, _child = child) 105 | } 106 | 107 | override fun fillMaxWidth(fraction: Float): T { 108 | 109 | velocityModifier = if (velocityModifier != null) { 110 | velocityModifier!! 111 | .fillMaxWidth(fraction = fraction) 112 | } else { 113 | Modifier.fillMaxWidth(fraction = fraction) 114 | } 115 | 116 | return _child!! 117 | } 118 | 119 | override fun fillMaxHeight(fraction: Float): T { 120 | velocityModifier = if (velocityModifier != null) { 121 | velocityModifier!! 122 | .fillMaxHeight(fraction = fraction) 123 | } else { 124 | Modifier.fillMaxHeight(fraction = fraction) 125 | } 126 | 127 | return _child!! 128 | } 129 | 130 | override fun fillMaxSize(fraction: Float): T { 131 | velocityModifier = if (velocityModifier != null) { 132 | velocityModifier!! 133 | .fillMaxSize(fraction = fraction) 134 | } else { 135 | Modifier.fillMaxSize(fraction = fraction) 136 | } 137 | 138 | return _child!! 139 | } 140 | 141 | 142 | override fun offset(x: Dp, y: Dp): T { 143 | velocityModifier = if (velocityModifier != null) { 144 | velocityModifier!! 145 | .offset(x = x, y = y) 146 | } else { 147 | Modifier.offset(x = x, y = y) 148 | } 149 | 150 | return _child!! 151 | } 152 | 153 | @Composable 154 | override fun square(size: Dp): T { 155 | velocityModifier = if (velocityModifier != null) { 156 | velocityModifier!! 157 | .requiredSize(size) 158 | } else { 159 | Modifier.requiredSize(size) 160 | } 161 | 162 | return _child!! 163 | } 164 | 165 | @Composable 166 | override fun forcedWidth(width: Dp): T { 167 | velocityModifier = if (velocityModifier != null) { 168 | velocityModifier!! 169 | .requiredWidth(width) 170 | } else { 171 | Modifier.requiredWidth(width) 172 | } 173 | 174 | return _child!! 175 | } 176 | 177 | @Composable 178 | override fun forcedHeight(height: Dp): T { 179 | velocityModifier = if (velocityModifier != null) { 180 | velocityModifier!! 181 | .requiredHeight(height) 182 | } else { 183 | Modifier.requiredHeight(height) 184 | } 185 | 186 | return _child!! 187 | } 188 | 189 | @Composable 190 | override fun wPCT(w: Number): T { 191 | val screenWidth = LocalConfiguration.current.screenWidthDp 192 | val width = (screenWidth / 100.0) * w.toDouble() 193 | velocityModifier = if (velocityModifier != null) { 194 | velocityModifier!! 195 | .requiredWidth(width.dp) 196 | } else { 197 | Modifier.requiredWidth(width.dp) 198 | } 199 | return _child!! 200 | } 201 | 202 | @Composable 203 | override fun hPCT(h: Number): T { 204 | val screenHeight = LocalConfiguration.current.screenHeightDp 205 | val width = (screenHeight / 100.0) * h.toDouble() 206 | velocityModifier = if (velocityModifier != null) { 207 | velocityModifier!! 208 | .requiredHeight(width.dp) 209 | } else { 210 | Modifier.requiredHeight(width.dp) 211 | } 212 | return _child!! 213 | } 214 | 215 | @Composable 216 | override fun whPCT(v: Number): T { 217 | val screenWidth = LocalConfiguration.current.screenWidthDp 218 | val screenHeight = LocalConfiguration.current.screenHeightDp 219 | val width = (screenWidth / 100.0) * v.toDouble() 220 | val height = (screenHeight / 100.0) * v.toDouble() 221 | velocityModifier = if (velocityModifier != null) { 222 | velocityModifier!! 223 | .requiredWidth(width.dp) 224 | .requiredHeight(height.dp) 225 | } else { 226 | Modifier 227 | .requiredWidth(width.dp) 228 | .requiredHeight(height.dp) 229 | } 230 | return _child!! 231 | } 232 | 233 | 234 | override fun modifier(value: Modifier): T { 235 | velocityModifier = value 236 | return _child!! 237 | } 238 | 239 | override fun width(value: Dp): T { 240 | velocityModifier = if (velocityModifier != null) { 241 | velocityModifier!!.width(value) 242 | } else { 243 | Modifier.width(value) 244 | } 245 | 246 | return _child!! 247 | } 248 | 249 | override fun aspectRatio(ratio: Float, matchHeightConstraintsFirst: Boolean): T { 250 | velocityModifier = if (velocityModifier != null) { 251 | velocityModifier!!.aspectRatio( 252 | ratio = ratio, 253 | matchHeightConstraintsFirst = matchHeightConstraintsFirst 254 | ) 255 | } else { 256 | Modifier.aspectRatio( 257 | ratio = ratio, 258 | matchHeightConstraintsFirst = matchHeightConstraintsFirst 259 | ) 260 | } 261 | 262 | return _child!! 263 | } 264 | 265 | override fun p(value: Dp): T { 266 | velocityModifier = if (velocityModifier != null) { 267 | velocityModifier!!.padding(value) 268 | } else { 269 | Modifier.padding(value) 270 | } 271 | 272 | return _child!! 273 | } 274 | 275 | override fun p(value: PaddingValues): T { 276 | velocityModifier = if (velocityModifier != null) { 277 | velocityModifier!!.padding(value) 278 | } else { 279 | Modifier.padding(value) 280 | } 281 | 282 | return _child!! 283 | } 284 | 285 | override fun pLTRB(left: Dp, top: Dp, right: Dp, bottom: Dp): T { 286 | velocityModifier = if (velocityModifier != null) { 287 | velocityModifier!!.padding(start = left, top = top, end = right, bottom = bottom) 288 | } else { 289 | Modifier.padding(start = left, top = top, end = right, bottom = bottom) 290 | } 291 | 292 | return _child!! 293 | } 294 | 295 | override fun pBaseline(top: Dp, bottom: Dp): T { 296 | velocityModifier = if (velocityModifier != null) { 297 | velocityModifier!!.paddingFromBaseline(top = top, bottom = bottom) 298 | } else { 299 | Modifier.paddingFromBaseline(top = top, bottom = bottom) 300 | } 301 | 302 | return _child!! 303 | } 304 | 305 | override fun withRounded(value: Dp): T { 306 | velocityModifier = if (velocityModifier != null) { 307 | velocityModifier!!.clip(RoundedCornerShape(value)) 308 | } else { 309 | Modifier.clip(RoundedCornerShape(value)) 310 | } 311 | 312 | return _child!! 313 | } 314 | 315 | override fun withShadow(value: Dp): T { 316 | velocityModifier = if (velocityModifier != null) { 317 | velocityModifier!!.shadow(500.dp) 318 | } else { 319 | Modifier.shadow(value) 320 | 321 | } 322 | 323 | return _child!! 324 | } 325 | 326 | override fun px(value: Dp): T { 327 | velocityModifier = if (velocityModifier != null) { 328 | velocityModifier!!.padding(horizontal = value) 329 | } else { 330 | Modifier.padding(horizontal = value) 331 | } 332 | 333 | return _child!! 334 | } 335 | 336 | override fun py(value: Dp): T { 337 | velocityModifier = if (velocityModifier != null) { 338 | velocityModifier!!.padding(vertical = value) 339 | } else { 340 | Modifier.padding(vertical = value) 341 | } 342 | 343 | return _child!! 344 | } 345 | 346 | override fun pxy(value1: Dp, value2: Dp): T { 347 | velocityModifier = if (velocityModifier != null) { 348 | velocityModifier!!.padding(horizontal = value1, vertical = value2) 349 | } else { 350 | Modifier.padding(horizontal = value1, vertical = value2) 351 | } 352 | 353 | return _child!! 354 | } 355 | 356 | override fun size(value: Dp): T { 357 | velocityModifier = if (velocityModifier != null) { 358 | velocityModifier!!.size(value) 359 | } else { 360 | Modifier.size(value) 361 | } 362 | 363 | return _child!! 364 | } 365 | 366 | override fun sizeIn(minWidth: Dp, maxWidth: Dp, minHeight: Dp, maxHeight: Dp): T { 367 | velocityModifier = if (velocityModifier != null) { 368 | velocityModifier!!.sizeIn( 369 | minWidth = minWidth, 370 | maxWidth = maxWidth, 371 | minHeight = minHeight, 372 | maxHeight = maxHeight 373 | ) 374 | } else { 375 | Modifier.sizeIn( 376 | minWidth = minWidth, 377 | maxWidth = maxWidth, 378 | minHeight = minHeight, 379 | maxHeight = maxHeight 380 | ) 381 | } 382 | 383 | return _child!! 384 | } 385 | 386 | 387 | override fun size(width: Dp, height: Dp): T { 388 | velocityModifier = if (velocityModifier != null) { 389 | velocityModifier!!.size(width, height) 390 | } else { 391 | Modifier.size(width, height) 392 | } 393 | 394 | return _child!! 395 | } 396 | 397 | override fun clip(shape: Shape): T { 398 | velocityModifier = if (velocityModifier != null) { 399 | velocityModifier!!.clip(shape) 400 | } else { 401 | Modifier.clip(shape) 402 | } 403 | 404 | return _child!! 405 | } 406 | 407 | override fun bg(color: Color, shape: Shape): T { 408 | velocityModifier = if (velocityModifier != null) { 409 | velocityModifier!!.background(color = color, shape = shape) 410 | } else { 411 | Modifier.background(color = color, shape = shape) 412 | } 413 | 414 | return _child!! 415 | } 416 | 417 | override fun clickable(onClick: () -> Unit, enabled: Boolean): T { 418 | velocityModifier = if (velocityModifier != null) { 419 | velocityModifier!!.clickable(enabled = enabled, onClick = onClick) 420 | } else { 421 | Modifier.clickable(enabled = enabled, onClick = onClick) 422 | } 423 | 424 | return _child!! 425 | } 426 | 427 | 428 | override fun testTag(tag: String): T { 429 | velocityModifier = if (velocityModifier != null) { 430 | velocityModifier!!.testTag(tag) 431 | } else { 432 | Modifier.testTag(tag) 433 | } 434 | 435 | return _child!! 436 | } 437 | 438 | override fun scrollHorizontal( 439 | state: ScrollState, 440 | enabled: Boolean, 441 | flingBehavior: FlingBehavior?, 442 | reverseScrolling: Boolean 443 | ): T { 444 | velocityModifier = if (velocityModifier != null) { 445 | velocityModifier!!.horizontalScroll(state, enabled, flingBehavior, reverseScrolling) 446 | } else { 447 | Modifier.horizontalScroll(state, enabled, flingBehavior, reverseScrolling) 448 | } 449 | 450 | return _child!! 451 | } 452 | 453 | override fun scrollVertical( 454 | state: ScrollState, 455 | enabled: Boolean, 456 | flingBehavior: FlingBehavior?, 457 | reverseScrolling: Boolean 458 | ): T { 459 | velocityModifier = if (velocityModifier != null) { 460 | velocityModifier!!.verticalScroll(state, enabled, flingBehavior, reverseScrolling) 461 | } else { 462 | Modifier.verticalScroll(state, enabled, flingBehavior, reverseScrolling) 463 | } 464 | 465 | return _child!! 466 | } 467 | 468 | 469 | /** 470 | * Modify element to add border with appearance specified with a [border] and a [shape] and clip it. 471 | * 472 | * @param [BorderStroke] class that specifies border appearance, such as size and color 473 | * @param shape shape of the border 474 | */ 475 | 476 | override fun border(width: Dp?, color: Color?, shape: Shape?): T { 477 | velocityModifier = if (velocityModifier != null) { 478 | velocityModifier!!.border( 479 | border = BorderStroke(width = width!!, color = color!!), 480 | shape = shape!! 481 | ) 482 | 483 | } else { 484 | Modifier.border( 485 | border = BorderStroke(width = width!!, color = color!!), 486 | shape = shape!! 487 | ) 488 | } 489 | 490 | return _child!! 491 | } 492 | 493 | 494 | override fun rotate(degrees: Float): T { 495 | return vxTransform!!.rotate(degrees) 496 | } 497 | 498 | override fun scale(x: Float, y: Float): T { 499 | return vxTransform!!.scale(x, y) 500 | } 501 | 502 | override fun scale(scale: Float): T { 503 | return vxTransform!!.scale(scale) 504 | } 505 | 506 | override fun linearGradient( 507 | colorStops: Array>?, 508 | colors: List?, 509 | start: Offset, 510 | end: Offset, 511 | tileMode: TileMode 512 | ): T { 513 | return vxGradient!!.linearGradient(colorStops, colors, start, end, tileMode) 514 | } 515 | 516 | override fun radialGradient( 517 | colorStops: Array>?, 518 | colors: List?, 519 | center: Offset, 520 | radius: Float, 521 | tileMode: TileMode 522 | ): T { 523 | return vxGradient!!.radialGradient(colorStops, colors, center, radius, tileMode) 524 | } 525 | 526 | override fun sweepGradient( 527 | colorStops: Array>?, 528 | colors: List?, 529 | center: Offset 530 | ): T { 531 | return vxGradient!!.sweepGradient(colorStops, colors, center) 532 | } 533 | 534 | 535 | } -------------------------------------------------------------------------------- /VelocityX/src/main/java/dev/codepur/velocityx/mixin/VxPaddingMixin.kt: -------------------------------------------------------------------------------- 1 | package dev.codepur.velocityx.mixin 2 | 3 | import androidx.compose.foundation.layout.PaddingValues 4 | import androidx.compose.ui.unit.Dp 5 | import androidx.compose.ui.unit.dp 6 | 7 | interface IVxPaddingMixin { 8 | fun p(value: Dp): T 9 | fun p(value: PaddingValues): T 10 | fun px(value: Dp): T 11 | fun py(value: Dp): T 12 | fun pxy(value1: Dp, value2: Dp): T 13 | fun pLTRB(left: Dp, top: Dp, right: Dp, bottom: Dp): T 14 | fun pBaseline(top: Dp, bottom: Dp): T 15 | 16 | /// Padding for all 17 | val p0: T 18 | get() = p(0.dp) 19 | val p1: T 20 | get() = p(1.dp) 21 | val p2: T 22 | get() = p(2.dp) 23 | val p4: T 24 | get() = p(4.dp) 25 | val p8: T 26 | get() = p(8.dp) 27 | val p12: T 28 | get() = p(12.dp) 29 | val p16: T 30 | get() = p(16.dp) 31 | val p20: T 32 | get() = p(20.dp) 33 | val p24: T 34 | get() = p(24.dp) 35 | val p32: T 36 | get() = p(32.dp) 37 | val p64: T 38 | get() = p(64.dp) 39 | 40 | /// Horizontal padding 41 | val px0: T 42 | get() = px(0.dp) 43 | val px1: T 44 | get() = px(1.dp) 45 | val px2: T 46 | get() = px(2.dp) 47 | val px4: T 48 | get() = px(4.dp) 49 | val px8: T 50 | get() = px(8.dp) 51 | val px12: T 52 | get() = px(12.dp) 53 | val px16: T 54 | get() = px(16.dp) 55 | val px20: T 56 | get() = px(20.dp) 57 | val px24: T 58 | get() = px(24.dp) 59 | val px32: T 60 | get() = px(32.dp) 61 | val px64: T 62 | get() = px(64.dp) 63 | 64 | /// Vertical padding 65 | val py0: T 66 | get() = py(0.dp) 67 | val py1: T 68 | get() = py(1.dp) 69 | val py2: T 70 | get() = py(2.dp) 71 | val py4: T 72 | get() = py(4.dp) 73 | val py8: T 74 | get() = py(8.dp) 75 | val py12: T 76 | get() = py(12.dp) 77 | val py16: T 78 | get() = py(16.dp) 79 | val py20: T 80 | get() = py(20.dp) 81 | val py24: T 82 | get() = py(24.dp) 83 | val py32: T 84 | get() = py(32.dp) 85 | val py64: T 86 | get() = py(64.dp) 87 | 88 | 89 | /// Horizontal & Vertical padding 90 | val pxy0: T 91 | get() = pxy(0.dp, 0.dp) 92 | val pxy1: T 93 | get() = pxy(1.dp, 1.dp) 94 | val pxy2: T 95 | get() = pxy(2.dp, 2.dp) 96 | val pxy4: T 97 | get() = pxy(4.dp, 4.dp) 98 | val pxy8: T 99 | get() = pxy(8.dp, 8.dp) 100 | val pxy12: T 101 | get() = pxy(12.dp, 12.dp) 102 | val pxy16: T 103 | get() = pxy(16.dp, 16.dp) 104 | val pxy20: T 105 | get() = pxy(20.dp, 20.dp) 106 | val pxy24: T 107 | get() = pxy(24.dp, 24.dp) 108 | val pxy32: T 109 | get() = pxy(32.dp, 32.dp) 110 | val pxy64: T 111 | get() = pxy(64.dp, 64.dp) 112 | 113 | } -------------------------------------------------------------------------------- /VelocityX/src/main/java/dev/codepur/velocityx/mixin/VxRowColumnAlignment.kt: -------------------------------------------------------------------------------- 1 | package dev.codepur.velocityx.mixin 2 | 3 | import androidx.compose.foundation.layout.Arrangement 4 | import androidx.compose.ui.Alignment 5 | import androidx.compose.ui.unit.dp 6 | 7 | interface IVxRowColumnAlignmentMixin { 8 | 9 | var horizontalArrangement: Arrangement.Horizontal? 10 | var verticalArrangement: Arrangement.Vertical? 11 | var verticalAlignment: Alignment.Vertical? 12 | var horizontalAlignment: Alignment.Horizontal? 13 | 14 | val arrangeStart: T 15 | get() = horizontalArrangement(value = Arrangement.Start) 16 | 17 | val arrangeEnd: T 18 | get() = horizontalArrangement(value = Arrangement.End) 19 | 20 | val arrangeCenter: T 21 | get() = horizontalArrangement(value = Arrangement.Center) 22 | 23 | val arrangeSpaceAround: T 24 | get() = horizontalArrangement(value = Arrangement.SpaceAround) 25 | 26 | val arrangeSpaceBetween: T 27 | get() = horizontalArrangement(value = Arrangement.SpaceBetween) 28 | 29 | val arrangeSpaceEvenly: T 30 | get() = horizontalArrangement(value = Arrangement.SpaceEvenly) 31 | 32 | val arrangeTop: T 33 | get() = verticalArrangement(value = Arrangement.Top) 34 | 35 | val arrangeBottom: T 36 | get() = verticalArrangement(value = Arrangement.Bottom) 37 | 38 | val alignTop: T 39 | get() = verticalAlignment(value = Alignment.Top) 40 | 41 | val alignCenterVertical: T 42 | get() = verticalAlignment(value = Alignment.CenterVertically) 43 | 44 | val alignBottom: T 45 | get() = verticalAlignment(value = Alignment.Bottom) 46 | 47 | val alignStart: T 48 | get() = horizontalAlignment(value = Alignment.Start) 49 | 50 | val alignCenterHorizontal: T 51 | get() = horizontalAlignment(value = Alignment.CenterHorizontally) 52 | 53 | val alignEnd: T 54 | get() = horizontalAlignment(value = Alignment.End) 55 | 56 | fun arrangeSpacedBy(spacing: Number): T = 57 | horizontalArrangement(value = Arrangement.spacedBy(spacing.toDouble().dp)) 58 | 59 | fun setChildForRowColumnAlignment(child: T) 60 | 61 | fun arrangement(value: Arrangement.HorizontalOrVertical): T 62 | 63 | fun horizontalArrangement(value: Arrangement.Horizontal): T 64 | 65 | fun verticalArrangement(value: Arrangement.Vertical): T 66 | 67 | fun horizontalAlignment(value: Alignment.Horizontal): T 68 | 69 | fun verticalAlignment(value: Alignment.Vertical): T 70 | 71 | } 72 | 73 | class VxRowColumnAlignmentMixin : IVxRowColumnAlignmentMixin { 74 | private var _child: T? = null 75 | 76 | override var horizontalArrangement: Arrangement.Horizontal? = null 77 | override var verticalArrangement: Arrangement.Vertical? = null 78 | override var verticalAlignment: Alignment.Vertical? = null 79 | override var horizontalAlignment: Alignment.Horizontal? = null 80 | 81 | override fun setChildForRowColumnAlignment(child: T) { 82 | _child = child 83 | } 84 | 85 | override fun arrangement(value: Arrangement.HorizontalOrVertical): T { 86 | horizontalArrangement = value 87 | verticalArrangement = value 88 | return _child!! 89 | } 90 | 91 | override fun horizontalArrangement(value: Arrangement.Horizontal): T { 92 | horizontalArrangement = value 93 | return _child!! 94 | } 95 | 96 | override fun verticalArrangement(value: Arrangement.Vertical): T { 97 | verticalArrangement = value 98 | return _child!! 99 | } 100 | 101 | override fun horizontalAlignment(value: Alignment.Horizontal): T { 102 | horizontalAlignment = value 103 | return _child!! 104 | 105 | } 106 | 107 | override fun verticalAlignment(value: Alignment.Vertical): T { 108 | verticalAlignment = value 109 | return _child!! 110 | 111 | } 112 | 113 | 114 | } 115 | -------------------------------------------------------------------------------- /VelocityX/src/main/java/dev/codepur/velocityx/mixin/VxSizeMixin.kt: -------------------------------------------------------------------------------- 1 | package dev.codepur.velocityx.mixin 2 | 3 | import androidx.compose.runtime.Composable 4 | import androidx.compose.ui.unit.Dp 5 | 6 | interface IVxSizeMixin { 7 | fun width(value: Dp): T 8 | fun size(value: Dp): T 9 | fun size(width: Dp, height: Dp): T 10 | fun sizeIn(minWidth: Dp, maxWidth: Dp, minHeight: Dp, maxHeight: Dp): T 11 | fun aspectRatio(ratio: Float, matchHeightConstraintsFirst: Boolean = false): T 12 | fun offset(x: Dp, y: Dp): T 13 | 14 | fun fillMaxWidth(fraction: Float): T 15 | fun fillMaxHeight(fraction: Float): T 16 | fun fillMaxSize(fraction: Float): T 17 | 18 | @Composable 19 | fun square(size: Dp): T 20 | 21 | @Composable 22 | fun wPCT(w: Number): T 23 | 24 | @Composable 25 | fun hPCT(h: Number): T 26 | 27 | @Composable 28 | fun whPCT(v: Number): T 29 | 30 | @Composable 31 | fun forcedWidth(width: Dp): T 32 | 33 | @Composable 34 | fun forcedHeight(height: Dp): T 35 | 36 | @Composable 37 | fun w0(): T = wPCT(w = 0.0) 38 | 39 | @Composable 40 | fun w1(): T = wPCT(w = 1.0) 41 | 42 | @Composable 43 | fun w2(): T = wPCT(w = 2.0) 44 | 45 | @Composable 46 | fun w4(): T = wPCT(w = 4.0) 47 | 48 | @Composable 49 | fun w8(): T = wPCT(w = 8.0) 50 | 51 | @Composable 52 | fun w10(): T = wPCT(w = 10.0) 53 | 54 | @Composable 55 | fun w12(): T = wPCT(w = 12.0) 56 | 57 | @Composable 58 | fun w16(): T = wPCT(w = 16.0) 59 | 60 | @Composable 61 | fun w20(): T = wPCT(w = 20.0) 62 | 63 | @Composable 64 | fun w24(): T = wPCT(w = 24.0) 65 | 66 | @Composable 67 | fun w32(): T = wPCT(w = 32.0) 68 | 69 | @Composable 70 | fun w40(): T = wPCT(w = 40.0) 71 | 72 | @Composable 73 | fun w48(): T = wPCT(w = 48.0) 74 | 75 | @Composable 76 | fun w60(): T = wPCT(w = 60.0) 77 | 78 | @Composable 79 | fun w75(): T = wPCT(w = 75.0) 80 | 81 | @Composable 82 | fun wHalf(): T = wPCT(w = 50.0) 83 | 84 | @Composable 85 | fun wOneThird(): T = wPCT(w = 33.33) 86 | 87 | @Composable 88 | fun wTwoThird(): T = wPCT(w = 66.66) 89 | 90 | @Composable 91 | fun wOneForth(): T = wPCT(w = 23.0) 92 | 93 | @Composable 94 | fun wThreeForth(): T = wPCT(w = 75.0) 95 | 96 | @Composable 97 | fun wFull(): T = wPCT(w = 100.0) 98 | 99 | 100 | @Composable 101 | fun h0(): T = hPCT(h = 0.0) 102 | 103 | @Composable 104 | fun h1(): T = hPCT(h = 1.0) 105 | 106 | @Composable 107 | fun h2(): T = hPCT(h = 2.0) 108 | 109 | @Composable 110 | fun h4(): T = hPCT(h = 4.0) 111 | 112 | @Composable 113 | fun h8(): T = hPCT(h = 8.0) 114 | 115 | @Composable 116 | fun h10(): T = hPCT(h = 10.0) 117 | 118 | @Composable 119 | fun h12(): T = hPCT(h = 12.0) 120 | 121 | @Composable 122 | fun h16(): T = hPCT(h = 16.0) 123 | 124 | @Composable 125 | fun h20(): T = hPCT(h = 20.0) 126 | 127 | @Composable 128 | fun h24(): T = hPCT(h = 24.0) 129 | 130 | @Composable 131 | fun h32(): T = hPCT(h = 32.0) 132 | 133 | @Composable 134 | fun h40(): T = hPCT(h = 40.0) 135 | 136 | @Composable 137 | fun h48(): T = hPCT(h = 48.0) 138 | 139 | @Composable 140 | fun h60(): T = hPCT(h = 60.0) 141 | 142 | @Composable 143 | fun h75(): T = hPCT(h = 75.0) 144 | 145 | @Composable 146 | fun hHalf(): T = hPCT(h = 50.0) 147 | 148 | @Composable 149 | fun hOneThird(): T = hPCT(h = 33.33) 150 | 151 | @Composable 152 | fun hThoThird(): T = hPCT(h = 66.66) 153 | 154 | @Composable 155 | fun hOneForth(): T = hPCT(h = 23.0) 156 | 157 | @Composable 158 | fun hThreeForth(): T = hPCT(h = 75.0) 159 | 160 | @Composable 161 | fun hFull(): T = hPCT(h = 100.0) 162 | 163 | @Composable 164 | fun wh0(): T = whPCT(v = 0.0) 165 | 166 | @Composable 167 | fun wh1(): T = whPCT(v = 1.0) 168 | 169 | @Composable 170 | fun wh2(): T = whPCT(v = 2.0) 171 | 172 | @Composable 173 | fun wh4(): T = whPCT(v = 4.0) 174 | 175 | @Composable 176 | fun wh8(): T = whPCT(v = 8.0) 177 | 178 | @Composable 179 | fun wh10(): T = whPCT(v = 10.0) 180 | 181 | @Composable 182 | fun wh12(): T = whPCT(v = 12.0) 183 | 184 | @Composable 185 | fun wh16(): T = whPCT(v = 16.0) 186 | 187 | @Composable 188 | fun wh20(): T = whPCT(v = 20.0) 189 | 190 | @Composable 191 | fun wh24(): T = whPCT(v = 24.0) 192 | 193 | @Composable 194 | fun wh32(): T = whPCT(v = 32.0) 195 | 196 | @Composable 197 | fun wh40(): T = whPCT(v = 40.0) 198 | 199 | @Composable 200 | fun wh48(): T = whPCT(v = 48.0) 201 | 202 | @Composable 203 | fun wh60(): T = whPCT(v = 60.0) 204 | 205 | @Composable 206 | fun wh75(): T = whPCT(v = 75.0) 207 | 208 | @Composable 209 | fun whHalf(): T = whPCT(v = 50.0) 210 | 211 | @Composable 212 | fun whOneThird(): T = whPCT(v = 33.33) 213 | 214 | @Composable 215 | fun whTwoThird(): T = whPCT(v = 66.66) 216 | 217 | @Composable 218 | fun whOneForth(): T = whPCT(v = 23.0) 219 | 220 | @Composable 221 | fun whThreeForth(): T = whPCT(v = 75.0) 222 | 223 | @Composable 224 | fun whFull(): T = whPCT(v = 100.0) 225 | } -------------------------------------------------------------------------------- /VelocityX/src/main/java/dev/codepur/velocityx/mixin/VxTransformMixin.kt: -------------------------------------------------------------------------------- 1 | package dev.codepur.velocityx.mixin 2 | 3 | import androidx.compose.ui.Modifier 4 | import androidx.compose.ui.draw.rotate 5 | import androidx.compose.ui.draw.scale 6 | 7 | interface IVxTransformMixin { 8 | fun rotate(degrees: Float): T 9 | fun scale(x: Float, y: Float): T 10 | fun scale(scale: Float): T 11 | 12 | /// Rotation 13 | val rotate0: T 14 | get() = rotate(0f) 15 | val rotate15: T 16 | get() = rotate(15f) 17 | val rotateN15: T 18 | get() = rotate(-15f) 19 | val rotate30: T 20 | get() = rotate(30f) 21 | val rotateN30: T 22 | get() = rotate(-30f) 23 | val rotate45: T 24 | get() = rotate(45f) 25 | val rotateN45: T 26 | get() = rotate(-45f) 27 | val rotate60: T 28 | get() = rotate(60f) 29 | val rotateN60: T 30 | get() = rotate(-60f) 31 | val rotate75: T 32 | get() = rotate(75f) 33 | val rotateN75: T 34 | get() = rotate(-75f) 35 | val rotate90: T 36 | get() = rotate(90f) 37 | val rotateN90: T 38 | get() = rotate(-90f) 39 | val rotate120: T 40 | get() = rotate(120f) 41 | val rotateN120: T 42 | get() = rotate(-120f) 43 | val rotate180: T 44 | get() = rotate(180f) 45 | val rotateN180: T 46 | get() = rotate(-180f) 47 | val rotate270: T 48 | get() = rotate(270f) 49 | val rotateN270: T 50 | get() = rotate(-270f) 51 | 52 | 53 | /// Scaling 54 | val scale0: T 55 | get() = scale(0f, y = 0f) 56 | val scale50: T 57 | get() = scale(0.5f, y = 0.5f) 58 | val scale100: T 59 | get() = scale(1f, y = 1f) 60 | val scale150: T 61 | get() = scale(1.5f, y = 1.5f) 62 | val scale200: T 63 | get() = scale(2f, y = 2f) 64 | val scaleN200: T 65 | get() = scale(-2f, y = -2f) 66 | } 67 | 68 | class VxTransformMixin(private var vxModifierMixin: VxModifierMixin, private val _child: T?) : 69 | IVxTransformMixin { 70 | 71 | override fun rotate(degrees: Float): T { 72 | vxModifierMixin.velocityModifier = if (vxModifierMixin.velocityModifier != null) { 73 | vxModifierMixin.velocityModifier!!.rotate(degrees = degrees) 74 | } else { 75 | Modifier.rotate(degrees = degrees) 76 | } 77 | 78 | return _child!! 79 | } 80 | 81 | override fun scale(x: Float, y: Float): T { 82 | vxModifierMixin.velocityModifier = if (vxModifierMixin.velocityModifier != null) { 83 | vxModifierMixin.velocityModifier!!.scale(scaleX = x, scaleY = y) 84 | } else { 85 | Modifier.scale(scaleX = x, scaleY = y) 86 | } 87 | 88 | return _child!! 89 | } 90 | 91 | override fun scale(scale: Float): T { 92 | vxModifierMixin.velocityModifier = if (vxModifierMixin.velocityModifier != null) { 93 | vxModifierMixin.velocityModifier!!.scale(scale) 94 | } else { 95 | Modifier.scale(scale) 96 | } 97 | 98 | return _child!! 99 | } 100 | } -------------------------------------------------------------------------------- /VelocityX/src/test/java/dev/codepur/velocityx/ExampleUnitTest.kt: -------------------------------------------------------------------------------- 1 | package dev.codepur.velocityx 2 | 3 | import org.junit.Test 4 | 5 | import org.junit.Assert.* 6 | 7 | /** 8 | * Example local unit test, which will execute on the development machine (host). 9 | * 10 | * See [testing documentation](http://d.android.com/tools/testing). 11 | */ 12 | class ExampleUnitTest { 13 | @Test 14 | fun addition_isCorrect() { 15 | assertEquals(4, 2 + 2) 16 | } 17 | } -------------------------------------------------------------------------------- /app/.gitignore: -------------------------------------------------------------------------------- 1 | /build -------------------------------------------------------------------------------- /app/build.gradle: -------------------------------------------------------------------------------- 1 | plugins { 2 | id 'com.android.application' 3 | id 'org.jetbrains.kotlin.android' 4 | } 5 | 6 | android { 7 | compileSdk 33 8 | 9 | defaultConfig { 10 | applicationId "com.example.velocityx" 11 | minSdk 26 12 | targetSdk 33 13 | versionCode 1 14 | versionName "1.0" 15 | 16 | testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner" 17 | vectorDrawables { 18 | useSupportLibrary true 19 | } 20 | } 21 | 22 | buildTypes { 23 | release { 24 | minifyEnabled false 25 | proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro' 26 | } 27 | } 28 | compileOptions { 29 | sourceCompatibility JavaVersion.VERSION_1_8 30 | targetCompatibility JavaVersion.VERSION_1_8 31 | } 32 | kotlinOptions { 33 | jvmTarget = '1.8' 34 | } 35 | buildFeatures { 36 | compose true 37 | } 38 | composeOptions { 39 | kotlinCompilerExtensionVersion compose_version 40 | } 41 | packagingOptions { 42 | resources { 43 | excludes += '/META-INF/{AL2.0,LGPL2.1}' 44 | } 45 | } 46 | } 47 | 48 | dependencies { 49 | 50 | implementation 'androidx.core:core-ktx:1.7.0' 51 | implementation "androidx.compose.ui:ui:$compose_version" 52 | implementation 'androidx.compose.material3:material3:1.0.0-alpha14' 53 | implementation "androidx.compose.ui:ui-tooling-preview:$compose_version" 54 | implementation 'androidx.lifecycle:lifecycle-runtime-ktx:2.3.1' 55 | implementation 'androidx.activity:activity-compose:1.3.1' 56 | implementation project(path: ':VelocityX') 57 | testImplementation 'junit:junit:4.13.2' 58 | androidTestImplementation 'androidx.test.ext:junit:1.1.3' 59 | androidTestImplementation 'androidx.test.espresso:espresso-core:3.4.0' 60 | androidTestImplementation "androidx.compose.ui:ui-test-junit4:$compose_version" 61 | debugImplementation "androidx.compose.ui:ui-tooling:$compose_version" 62 | debugImplementation "androidx.compose.ui:ui-test-manifest:$compose_version" 63 | } -------------------------------------------------------------------------------- /app/proguard-rules.pro: -------------------------------------------------------------------------------- 1 | # Add project specific ProGuard rules here. 2 | # You can control the set of applied configuration files using the 3 | # proguardFiles setting in build.gradle. 4 | # 5 | # For more details, see 6 | # http://developer.android.com/guide/developing/tools/proguard.html 7 | 8 | # If your project uses WebView with JS, uncomment the following 9 | # and specify the fully qualified class name to the JavaScript interface 10 | # class: 11 | #-keepclassmembers class fqcn.of.javascript.interface.for.webview { 12 | # public *; 13 | #} 14 | 15 | # Uncomment this to preserve the line number information for 16 | # debugging stack traces. 17 | #-keepattributes SourceFile,LineNumberTable 18 | 19 | # If you keep the line number information, uncomment this to 20 | # hide the original source file name. 21 | #-renamesourcefileattribute SourceFile -------------------------------------------------------------------------------- /app/src/androidTest/java/com/example/velocityXAndroid/ExampleInstrumentedTest.kt: -------------------------------------------------------------------------------- 1 | package com.example.velocityXAndroid 2 | 3 | import androidx.test.platform.app.InstrumentationRegistry 4 | import androidx.test.ext.junit.runners.AndroidJUnit4 5 | 6 | import org.junit.Test 7 | import org.junit.runner.RunWith 8 | 9 | import org.junit.Assert.* 10 | 11 | /** 12 | * Instrumented test, which will execute on an Android device. 13 | * 14 | * See [testing documentation](http://d.android.com/tools/testing). 15 | */ 16 | @RunWith(AndroidJUnit4::class) 17 | class ExampleInstrumentedTest { 18 | @Test 19 | fun useAppContext() { 20 | // Context of the app under test. 21 | val appContext = InstrumentationRegistry.getInstrumentation().targetContext 22 | assertEquals("com.example.jc1", appContext.packageName) 23 | } 24 | } -------------------------------------------------------------------------------- /app/src/main/AndroidManifest.xml: -------------------------------------------------------------------------------- 1 | 2 | 5 | 6 | 16 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | -------------------------------------------------------------------------------- /app/src/main/java/com/example/velocityXAndroid/MainActivity.kt: -------------------------------------------------------------------------------- 1 | package com.example.velocityXAndroid 2 | 3 | import android.os.Bundle 4 | import androidx.activity.ComponentActivity 5 | import androidx.activity.compose.setContent 6 | import androidx.compose.foundation.layout.fillMaxSize 7 | import androidx.compose.material3.* 8 | import androidx.compose.runtime.Composable 9 | import androidx.compose.ui.Modifier 10 | import androidx.compose.ui.tooling.preview.Preview 11 | import com.example.velocityXAndroid.ui.theme.VxTheme 12 | import dev.codepur.velocityx.compose.* 13 | import dev.codepur.velocityx.extensions.timeAgo 14 | import java.time.LocalDateTime 15 | import java.time.format.DateTimeFormatter 16 | 17 | class MainActivity : ComponentActivity() { 18 | override fun onCreate(savedInstanceState: Bundle?) { 19 | super.onCreate(savedInstanceState) 20 | setContent { 21 | VxTheme { 22 | // A surface container using the 'background' color from the theme 23 | Surface( 24 | modifier = Modifier.fillMaxSize(), 25 | color = MaterialTheme.colorScheme.primary 26 | ) { 27 | VelocityXDemo() 28 | // BoxExample() 29 | } 30 | } 31 | } 32 | } 33 | } 34 | 35 | @OptIn(ExperimentalMaterial3Api::class) 36 | @Composable 37 | fun VelocityXDemo() { 38 | Scaffold( 39 | topBar = { 40 | SmallTopAppBar( 41 | title = { "VelocityX Example".text.semiBold.make() }, 42 | ) 43 | }, 44 | floatingActionButton = { 45 | FloatingActionButton(onClick = {}) { 46 | "Click Here".text.p16.make() 47 | } 48 | }, 49 | content = { pad -> 50 | VxColumn { 51 | "VxText Example".text.blue800.bold.xl2.make() 52 | HeightBox(20) 53 | VxBox { 54 | "VxBox Example".text.white.bold.p16.xl2.make() 55 | }.blue800.wFull().p16.rounded.make() 56 | HeightBox(20) 57 | VxImage(R.drawable.flpy).fit.roundedLg.make() 58 | HeightBox(20) 59 | VxRow { 60 | "VxRow Example".text.white.bold.p16.xl2.make() 61 | WidthBox(20) 62 | VxImage(R.drawable.flpy).fit.rounded.make() 63 | }.blue800.rounded.make() 64 | HeightBox(20) 65 | VxCard { 66 | "VxCard Example".text.blue800.bold.xl.p20.make() 67 | }.make() 68 | HeightBox(20) 69 | VxCard { 70 | LocalDateTime.parse("2020-03-04 11:30:40", DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss")).timeAgo(useShortForm=true).text.blue800.bold.xl.p20.make() 71 | }.make() 72 | 73 | }.p(pad).p16.make() 74 | }, 75 | 76 | ) 77 | 78 | 79 | } 80 | 81 | 82 | @Preview(showBackground = true) 83 | @Composable 84 | fun DefaultPreview() { 85 | VxTheme { 86 | VelocityXDemo() 87 | } 88 | } 89 | -------------------------------------------------------------------------------- /app/src/main/java/com/example/velocityXAndroid/ui/theme/Color.kt: -------------------------------------------------------------------------------- 1 | package com.example.velocityXAndroid.ui.theme 2 | 3 | import androidx.compose.ui.graphics.Color 4 | import dev.codepur.velocityx.Vx 5 | 6 | 7 | val Purple80 = Color(0xFFD0BCFF) 8 | val PurpleGrey80 = Color(0xFFCCC2DC) 9 | val Pink80 = Color(0xFFEFB8C8) 10 | 11 | val Purple40 = Color(0xFF6650a4) 12 | val PurpleGrey40 = Color(0xFF625b71) 13 | val Pink40 = Color(0xFF7D5260) 14 | 15 | val rose100 = Vx.rose100 -------------------------------------------------------------------------------- /app/src/main/java/com/example/velocityXAndroid/ui/theme/Theme.kt: -------------------------------------------------------------------------------- 1 | package com.example.velocityXAndroid.ui.theme 2 | 3 | import android.app.Activity 4 | import android.os.Build 5 | import androidx.compose.foundation.isSystemInDarkTheme 6 | import androidx.compose.material3.MaterialTheme 7 | import androidx.compose.material3.darkColorScheme 8 | import androidx.compose.material3.dynamicDarkColorScheme 9 | import androidx.compose.material3.dynamicLightColorScheme 10 | import androidx.compose.material3.lightColorScheme 11 | import androidx.compose.runtime.Composable 12 | import androidx.compose.runtime.SideEffect 13 | import androidx.compose.ui.graphics.toArgb 14 | import androidx.compose.ui.platform.LocalContext 15 | import androidx.compose.ui.platform.LocalView 16 | import androidx.core.view.ViewCompat 17 | 18 | private val DarkColorScheme = darkColorScheme( 19 | primary = Purple80, 20 | secondary = PurpleGrey80, 21 | tertiary = Pink80 22 | ) 23 | 24 | private val LightColorScheme = lightColorScheme( 25 | primary = Purple40, 26 | secondary = PurpleGrey40, 27 | tertiary = Pink40 28 | 29 | /* Other default colors to override 30 | background = Color(0xFFFFFBFE), 31 | surface = Color(0xFFFFFBFE), 32 | onPrimary = Color.White, 33 | onSecondary = Color.White, 34 | onTertiary = Color.White, 35 | onBackground = Color(0xFF1C1B1F), 36 | onSurface = Color(0xFF1C1B1F), 37 | */ 38 | ) 39 | 40 | @Composable 41 | fun VxTheme( 42 | darkTheme: Boolean = isSystemInDarkTheme(), 43 | // Dynamic color is available on Android 12+ 44 | dynamicColor: Boolean = true, 45 | content: @Composable () -> Unit 46 | ) { 47 | val colorScheme = when { 48 | dynamicColor && Build.VERSION.SDK_INT >= Build.VERSION_CODES.S -> { 49 | val context = LocalContext.current 50 | if (darkTheme) dynamicDarkColorScheme(context) else dynamicLightColorScheme(context) 51 | } 52 | darkTheme -> DarkColorScheme 53 | else -> LightColorScheme 54 | } 55 | val view = LocalView.current 56 | if (!view.isInEditMode) { 57 | SideEffect { 58 | (view.context as Activity).window.statusBarColor = colorScheme.primary.toArgb() 59 | ViewCompat.getWindowInsetsController(view)?.isAppearanceLightStatusBars = darkTheme 60 | } 61 | } 62 | 63 | MaterialTheme( 64 | colorScheme = colorScheme, 65 | typography = Typography, 66 | content = content 67 | ) 68 | } -------------------------------------------------------------------------------- /app/src/main/java/com/example/velocityXAndroid/ui/theme/Type.kt: -------------------------------------------------------------------------------- 1 | package com.example.velocityXAndroid.ui.theme 2 | 3 | import androidx.compose.material3.Typography 4 | import androidx.compose.ui.text.TextStyle 5 | import androidx.compose.ui.text.font.FontFamily 6 | import androidx.compose.ui.text.font.FontWeight 7 | import androidx.compose.ui.unit.sp 8 | 9 | // Set of Material typography styles to start with 10 | val Typography = Typography( 11 | bodyLarge = TextStyle( 12 | fontFamily = FontFamily.Default, 13 | fontWeight = FontWeight.Normal, 14 | fontSize = 16.sp, 15 | lineHeight = 24.sp, 16 | letterSpacing = 0.5.sp 17 | ) 18 | /* Other default text styles to override 19 | titleLarge = TextStyle( 20 | fontFamily = FontFamily.Default, 21 | fontWeight = FontWeight.Normal, 22 | fontSize = 22.sp, 23 | lineHeight = 28.sp, 24 | letterSpacing = 0.sp 25 | ), 26 | labelSmall = TextStyle( 27 | fontFamily = FontFamily.Default, 28 | fontWeight = FontWeight.Medium, 29 | fontSize = 11.sp, 30 | lineHeight = 16.sp, 31 | letterSpacing = 0.5.sp 32 | ) 33 | */ 34 | ) -------------------------------------------------------------------------------- /app/src/main/res/drawable-v24/flpy.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/iampawan/VelocityXAndroidCompose/59bfe8fdcbb36dc8a46bb2b5afaac7ae9b770ccd/app/src/main/res/drawable-v24/flpy.png -------------------------------------------------------------------------------- /app/src/main/res/drawable-v24/ic_launcher_foreground.xml: -------------------------------------------------------------------------------- 1 | 7 | 8 | 9 | 15 | 18 | 21 | 22 | 23 | 24 | 30 | -------------------------------------------------------------------------------- /app/src/main/res/drawable/ic_launcher_background.xml: -------------------------------------------------------------------------------- 1 | 2 | 7 | 10 | 15 | 20 | 25 | 30 | 35 | 40 | 45 | 50 | 55 | 60 | 65 | 70 | 75 | 80 | 85 | 90 | 95 | 100 | 105 | 110 | 115 | 120 | 125 | 130 | 135 | 140 | 145 | 150 | 155 | 160 | 165 | 170 | 171 | -------------------------------------------------------------------------------- /app/src/main/res/mipmap-anydpi-v26/ic_launcher.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | -------------------------------------------------------------------------------- /app/src/main/res/mipmap-anydpi-v26/ic_launcher_round.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | -------------------------------------------------------------------------------- /app/src/main/res/mipmap-hdpi/ic_launcher.webp: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/iampawan/VelocityXAndroidCompose/59bfe8fdcbb36dc8a46bb2b5afaac7ae9b770ccd/app/src/main/res/mipmap-hdpi/ic_launcher.webp -------------------------------------------------------------------------------- /app/src/main/res/mipmap-hdpi/ic_launcher_round.webp: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/iampawan/VelocityXAndroidCompose/59bfe8fdcbb36dc8a46bb2b5afaac7ae9b770ccd/app/src/main/res/mipmap-hdpi/ic_launcher_round.webp -------------------------------------------------------------------------------- /app/src/main/res/mipmap-mdpi/ic_launcher.webp: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/iampawan/VelocityXAndroidCompose/59bfe8fdcbb36dc8a46bb2b5afaac7ae9b770ccd/app/src/main/res/mipmap-mdpi/ic_launcher.webp -------------------------------------------------------------------------------- /app/src/main/res/mipmap-mdpi/ic_launcher_round.webp: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/iampawan/VelocityXAndroidCompose/59bfe8fdcbb36dc8a46bb2b5afaac7ae9b770ccd/app/src/main/res/mipmap-mdpi/ic_launcher_round.webp -------------------------------------------------------------------------------- /app/src/main/res/mipmap-xhdpi/ic_launcher.webp: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/iampawan/VelocityXAndroidCompose/59bfe8fdcbb36dc8a46bb2b5afaac7ae9b770ccd/app/src/main/res/mipmap-xhdpi/ic_launcher.webp -------------------------------------------------------------------------------- /app/src/main/res/mipmap-xhdpi/ic_launcher_round.webp: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/iampawan/VelocityXAndroidCompose/59bfe8fdcbb36dc8a46bb2b5afaac7ae9b770ccd/app/src/main/res/mipmap-xhdpi/ic_launcher_round.webp -------------------------------------------------------------------------------- /app/src/main/res/mipmap-xxhdpi/ic_launcher.webp: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/iampawan/VelocityXAndroidCompose/59bfe8fdcbb36dc8a46bb2b5afaac7ae9b770ccd/app/src/main/res/mipmap-xxhdpi/ic_launcher.webp -------------------------------------------------------------------------------- /app/src/main/res/mipmap-xxhdpi/ic_launcher_round.webp: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/iampawan/VelocityXAndroidCompose/59bfe8fdcbb36dc8a46bb2b5afaac7ae9b770ccd/app/src/main/res/mipmap-xxhdpi/ic_launcher_round.webp -------------------------------------------------------------------------------- /app/src/main/res/mipmap-xxxhdpi/ic_launcher.webp: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/iampawan/VelocityXAndroidCompose/59bfe8fdcbb36dc8a46bb2b5afaac7ae9b770ccd/app/src/main/res/mipmap-xxxhdpi/ic_launcher.webp -------------------------------------------------------------------------------- /app/src/main/res/mipmap-xxxhdpi/ic_launcher_round.webp: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/iampawan/VelocityXAndroidCompose/59bfe8fdcbb36dc8a46bb2b5afaac7ae9b770ccd/app/src/main/res/mipmap-xxxhdpi/ic_launcher_round.webp -------------------------------------------------------------------------------- /app/src/main/res/values/colors.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | #FFBB86FC 4 | #FF6200EE 5 | #FF3700B3 6 | #FF03DAC5 7 | #FF018786 8 | #FF000000 9 | #FFFFFFFF 10 | -------------------------------------------------------------------------------- /app/src/main/res/values/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | VelocityX Example 3 | -------------------------------------------------------------------------------- /app/src/main/res/values/themes.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 |