Compare commits

...

2 Commits

Author SHA1 Message Date
cyzoox 9f0cc75a3f added drawing pad 2024-07-11 09:27:35 +08:00
cyzoox 593041b19b Bug fix on admin side and building faas 2024-04-22 16:05:35 +08:00
106 changed files with 8662 additions and 3911 deletions

View File

@ -26,7 +26,7 @@ apply plugin: 'kotlin-android'
apply from: "$flutterRoot/packages/flutter_tools/gradle/flutter.gradle"
android {
compileSdkVersion flutter.compileSdkVersion
compileSdkVersion 34
ndkVersion "25.1.8937393"
compileOptions {
@ -44,9 +44,10 @@ android {
defaultConfig {
// TODO: Specify your own unique Application ID (https://developer.android.com/studio/build/application-id.html).
applicationId "com.example.unit2"
applicationId "com.app.rpass"
// You can update the following values to match your application needs.
// For more information, see: https://docs.flutter.dev/deployment/android#reviewing-the-build-configuration.
minSdkVersion flutter.minSdkVersion
targetSdkVersion flutter.targetSdkVersion
versionCode flutterVersionCode.toInteger()

View File

@ -1,12 +1,16 @@
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.example.unit2">
package="com.example.unit2"
>
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.MANAGE_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.ACCESS_MEDIA_LOCATION"/>
<uses-permission android:name="android.permission.INTERNET"/>
<uses-permission android:name="android.permission.CAMERA" />
<uses-permission android:name="android.permission.INSTALL_PACKAGES" />
<uses-permission android:name="android.permission.DELETE_PACKAGES" />
<uses-permission android:name="android.permission.READ_MEDIA_IMAGES"/>
<uses-permission android:name="android.permission.READ_MEDIA_VIDEO"/>
<application
android:label="uniT App"
android:name="${applicationName}"
@ -16,7 +20,8 @@ android:authorities = "${applicationId}.fileprovider"
android:exported = "false"
android:grantUriPermissions = "true"
android:name = "androidx.core.content.FileProvider"
android:usesCleartextTraffic="true">
android:usesCleartextTraffic="true"
android:requestLegacyExternalStorage="true">
<meta-data
android:name = "android.support.FILE_PROVIDER_PATHS"

Binary file not shown.

After

Width:  |  Height:  |  Size: 852 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 18 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 18 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 5.7 KiB

After

Width:  |  Height:  |  Size: 9.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 459 B

Binary file not shown.

After

Width:  |  Height:  |  Size: 8.7 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 8.7 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 3.6 KiB

After

Width:  |  Height:  |  Size: 4.9 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.3 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 30 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 30 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 7.9 KiB

After

Width:  |  Height:  |  Size: 14 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.9 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 61 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 61 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 12 KiB

After

Width:  |  Height:  |  Size: 29 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 4.1 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 101 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 101 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 17 KiB

After

Width:  |  Height:  |  Size: 45 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 443 B

View File

@ -0,0 +1,595 @@
<?xml version="1.0" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 20010904//EN"
"http://www.w3.org/TR/2001/REC-SVG-20010904/DTD/svg10.dtd">
<svg version="1.0" xmlns="http://www.w3.org/2000/svg"
width="1024.000000pt" height="1024.000000pt" viewBox="0 0 1024.000000 1024.000000"
preserveAspectRatio="xMidYMid meet">
<g transform="translate(0.000000,1024.000000) scale(0.100000,-0.100000)"
fill="#000000" stroke="none">
<path d="M3055 8904 c-44 -7 -125 -21 -180 -29 -147 -24 -285 -58 -335 -84 -9
-5 -31 -12 -50 -16 -49 -10 -264 -115 -349 -170 -117 -75 -329 -257 -416 -356
-220 -249 -387 -612 -425 -925 -5 -46 -15 -121 -20 -166 -14 -118 -14 -4106 1
-4236 38 -346 168 -668 387 -957 60 -79 212 -235 287 -295 222 -177 490 -308
770 -379 237 -59 115 -56 2345 -56 1929 0 2061 1 2155 18 456 82 805 261 1096
564 248 258 408 562 491 933 l23 105 0 2210 0 2210 -22 101 c-89 398 -253 706
-517 970 -91 90 -253 221 -317 254 -13 7 -36 23 -51 35 -32 27 -194 108 -270
135 -29 10 -82 29 -118 42 -36 14 -90 29 -120 35 -136 28 -180 35 -250 43 -41
5 -95 13 -120 19 -73 17 -3891 12 -3995 -5z m2365 -214 c553 -50 1073 -240
1580 -575 578 -382 1072 -973 1338 -1600 167 -394 237 -697 263 -1140 17 -293
-1 -799 -30 -828 -5 -5 -52 -5 -105 -1 l-96 7 0 549 0 549 -45 45 -45 44 -169
0 -168 0 -47 -41 -46 -41 0 -140 0 -140 -67 8 c-38 4 -93 8 -123 9 l-55 0 -3
301 -2 301 -99 97 c-84 82 -103 96 -118 88 -10 -6 -58 -52 -107 -102 l-88 -92
3 -309 4 -309 -39 -24 -39 -23 -34 38 -34 37 1 499 c1 274 2 509 3 523 l2 25
-275 3 c-151 1 -285 0 -297 -3 l-23 -5 0 -549 0 -550 -55 -31 c-30 -17 -57
-35 -60 -41 -4 -5 -9 -9 -13 -9 -4 0 -7 226 -7 501 0 395 -3 503 -13 506 -16
7 -104 -69 -372 -321 -36 -34 -80 -72 -97 -84 l-33 -23 0 -250 c0 -157 -4
-249 -10 -249 -5 0 -31 13 -57 29 -27 15 -120 69 -208 119 -88 50 -223 127
-300 171 -77 45 -151 81 -165 81 -14 0 -188 -91 -393 -205 -203 -113 -373
-205 -378 -205 -5 0 -9 98 -9 233 0 210 -2 235 -17 249 -10 9 -79 58 -153 110
-302 211 -422 290 -436 284 -11 -4 -14 -39 -14 -199 l0 -194 -87 -6 c-49 -3
-96 -9 -106 -13 -15 -5 -17 -3 -12 18 5 18 -1 33 -19 55 l-26 31 0 310 0 310
-72 64 c-40 36 -100 87 -134 114 -34 27 -116 95 -182 152 l-121 102 -191 0
c-115 0 -199 -4 -211 -11 -19 -10 -20 -23 -19 -497 0 -268 1 -537 0 -599 l0
-112 -127 -3 c-71 -2 -129 -2 -131 -2 -2 1 14 11 34 23 l36 22 -31 29 c-17 17
-34 30 -38 30 -5 0 -53 -41 -108 -91 -55 -50 -153 -133 -217 -185 -176 -143
-201 -181 -163 -255 19 -36 50 -49 116 -49 l49 0 0 -366 c0 -335 -1 -366 -16
-360 -36 14 -203 25 -276 19 -75 -6 -77 -5 -82 18 -27 121 -37 745 -17 954 71
710 362 1373 848 1936 109 125 336 349 453 446 545 450 1224 737 1870 791 151
13 595 14 730 2z m-1840 -50 c-8 -5 -19 -10 -25 -10 -5 0 -3 5 5 10 8 5 20 10
25 10 6 0 3 -5 -5 -10z m-963 -86 c-3 -3 -12 -4 -19 -1 -8 3 -5 6 6 6 11 1 17
-2 13 -5z m-37 -8 c0 -2 -7 -7 -16 -10 -8 -3 -12 -2 -9 4 6 10 25 14 25 6z
m5280 -160 c0 -2 -7 -7 -16 -10 -8 -3 -12 -2 -9 4 6 10 25 14 25 6z m311 -273
c13 -16 12 -17 -3 -4 -10 7 -18 15 -18 17 0 8 8 3 21 -13z m-6149 -248 c6 -14
15 -25 19 -25 5 0 6 -7 3 -15 -5 -11 -2 -13 12 -8 12 4 15 3 10 -5 -5 -8 1
-12 18 -12 13 0 31 -3 40 -6 23 -9 19 -49 -6 -67 -19 -12 -23 -24 -23 -68 0
-48 -2 -54 -22 -57 -13 -2 -35 5 -51 16 -26 19 -28 19 -49 2 -12 -10 -20 -20
-17 -22 2 -3 -7 -3 -20 -1 -40 8 -51 28 -38 69 9 32 8 37 -16 59 -14 13 -29
22 -34 19 -4 -3 -4 5 1 18 9 25 45 48 77 48 15 0 25 11 37 40 18 46 42 52 59
15z m6133 -23 c17 -36 24 -42 50 -42 43 0 54 -11 53 -48 -1 -18 -4 -29 -7 -24
-4 6 -16 2 -30 -9 -18 -15 -21 -23 -13 -31 25 -25 11 -88 -20 -88 -10 0 -16
-4 -13 -10 3 -5 1 -10 -4 -10 -6 0 -11 6 -11 13 0 8 -9 22 -19 32 -19 16 -21
16 -50 -5 -41 -29 -75 -24 -79 12 -2 15 1 35 7 46 8 15 4 24 -20 46 -16 15
-29 33 -29 40 0 23 36 43 68 38 32 -4 38 1 44 43 3 22 28 46 43 42 6 -2 19
-22 30 -45z m-341 -98 c3 -8 2 -12 -4 -9 -6 3 -10 10 -10 16 0 14 7 11 14 -7z
m-6272 -756 c-9 -9 -12 -7 -12 12 0 19 3 21 12 12 9 -9 9 -15 0 -24z m1396
-180 l55 -43 -189 -3 c-103 -1 -194 0 -201 2 -14 6 -17 43 -7 70 5 14 28 16
147 16 l140 0 55 -42z m82 -163 c0 -32 0 -32 -61 -39 -34 -3 -129 -6 -210 -6
l-149 0 -6 25 c-14 56 -13 56 216 54 l210 -1 0 -33z m-127 -125 l127 0 0 -28
0 -29 -205 -7 c-113 -4 -210 -4 -215 -1 -12 7 -13 58 -2 69 4 5 43 6 87 2 44
-3 137 -6 208 -6z m30 -150 c96 0 98 0 95 -22 -4 -31 -31 -35 -240 -37 l-178
-1 0 36 0 37 113 -6 c61 -4 156 -7 210 -7z m95 -150 c1 0 2 -7 2 -15 0 -27
-47 -35 -236 -41 l-184 -7 0 38 0 38 208 -6 c114 -3 208 -6 210 -7z m-211
-154 c11 -11 -12 -33 -35 -33 -14 0 -28 -6 -30 -12 -2 -6 -14 -11 -28 -11 -16
0 -22 4 -18 14 3 8 0 17 -6 21 -6 3 -10 3 -9 -2 5 -26 -4 -33 -41 -33 -38 0
-40 1 -40 33 l0 32 102 -3 c56 -1 103 -4 105 -6z m1036 -100 c9 -7 17 -17 17
-22 0 -4 -5 -3 -12 4 -7 7 -16 12 -21 12 -5 0 -2 -6 6 -14 8 -9 25 -13 38 -10
23 5 23 5 5 -10 -11 -9 -24 -16 -29 -16 -8 0 -7 -19 4 -59 2 -7 -2 -16 -9 -18
-7 -3 -11 3 -10 14 2 10 -1 18 -7 18 -5 0 -10 -19 -9 -42 0 -24 -3 -43 -8 -43
-4 0 -8 45 -8 100 0 104 5 115 43 86z m77 -57 c0 -6 -9 -9 -20 -6 -14 4 -20 0
-20 -11 0 -13 -3 -13 -12 -4 -10 10 -10 15 2 22 21 13 50 12 50 -1z m104 -60
c20 -12 35 -28 35 -37 -1 -16 -2 -16 -6 0 -5 19 -56 40 -77 32 -8 -3 -17 -1
-21 5 -3 7 0 8 9 5 9 -3 16 -1 16 5 0 15 3 14 44 -10z m2013 -1 c-3 -8 -6 -5
-6 6 -1 11 2 17 5 13 3 -3 4 -12 1 -19z m43 13 c0 -6 -4 -13 -10 -16 -5 -3
-10 1 -10 9 0 9 5 16 10 16 6 0 10 -4 10 -9z m-2810 -45 c0 -26 -31 -72 -68
-101 -43 -34 -51 -36 -96 -31 -48 5 -50 4 -94 -39 -51 -51 -48 -66 18 -86 l38
-12 -36 -49 c-40 -56 -36 -54 -116 -62 l-59 -6 5 43 c20 171 201 345 361 347
26 0 47 -2 47 -4z m680 -6 c0 -5 -7 -10 -16 -10 -8 0 -12 5 -9 10 3 6 10 10
16 10 5 0 9 -4 9 -10z m-85 -50 c3 -6 -1 -7 -9 -4 -18 7 -21 14 -7 14 6 0 13
-4 16 -10z m70 0 c3 -5 1 -10 -4 -10 -6 0 -11 5 -11 10 0 6 2 10 4 10 3 0 8
-4 11 -10z m-204 -76 c30 -9 75 -27 100 -39 50 -26 149 -101 149 -114 0 -4
-62 -11 -137 -15 -76 -4 -169 -11 -207 -16 -68 -8 -71 -8 -148 31 -42 21 -89
39 -102 39 -27 0 -86 -44 -86 -64 0 -7 18 -21 41 -32 l41 -20 -99 -61 c-54
-33 -103 -63 -109 -66 -6 -4 -26 6 -44 21 l-33 28 22 42 c34 67 146 173 227
215 125 65 272 84 385 51z m1644 -219 c160 -92 391 -225 515 -295 124 -70 266
-151 315 -180 50 -29 153 -89 229 -132 77 -44 158 -91 180 -105 l39 -25 -53
-26 c-65 -31 -59 -32 -247 74 -373 210 -441 249 -483 274 -25 15 -65 39 -90
52 -56 31 -409 236 -555 323 -100 60 -131 75 -154 75 -11 0 -71 -29 -133 -64
-62 -35 -198 -112 -303 -171 -164 -93 -333 -188 -770 -432 -231 -128 -286
-154 -317 -148 -18 4 -28 12 -25 19 4 9 -2 12 -16 9 -12 -2 -30 2 -40 9 -20
15 -93 -28 933 545 627 350 669 373 680 368 3 -2 136 -78 295 -170z m-2875
144 c91 -21 187 -94 239 -181 12 -21 21 -48 19 -60 -3 -21 -8 -23 -58 -22
-132 1 -370 18 -370 25 0 5 32 33 70 64 39 31 70 60 70 64 0 14 -41 61 -54 61
-20 0 -157 -89 -216 -140 l-56 -48 -147 -3 -146 -4 32 33 c71 75 239 175 337
202 98 27 186 30 280 9z m4409 -243 c67 -35 121 -83 121 -110 0 -45 -13 -47
-75 -10 -33 19 -84 46 -112 60 -29 14 -53 32 -53 40 0 8 -14 21 -32 28 -27 12
-29 15 -12 19 37 11 113 -2 163 -27z m-3235 -7 c3 -17 6 -109 6 -204 0 -170 0
-173 -23 -188 -23 -15 -25 -14 -68 45 -24 34 -72 86 -106 116 l-63 56 0 77 0
78 53 16 c65 19 133 32 168 34 22 1 28 -4 33 -30z m-650 -59 c48 -43 73 -102
95 -232 22 -130 35 -238 28 -238 -2 0 -31 16 -63 35 -32 19 -62 35 -67 35 -5
0 -24 7 -43 16 -24 12 -34 23 -34 40 0 13 -12 40 -26 61 -14 21 -30 57 -37 80
-6 24 -14 43 -18 43 -4 0 -10 -35 -14 -77 l-8 -78 -15 35 c-51 120 30 310 133
310 24 0 45 -9 69 -30z m4789 -26 c67 -17 139 -51 177 -83 23 -19 23 -20 5
-21 -11 0 -53 -7 -92 -17 l-73 -17 -67 28 c-38 15 -91 30 -119 33 -48 5 -53 3
-69 -20 -22 -34 -12 -62 25 -76 17 -6 44 -16 62 -23 l32 -12 -30 -13 c-74 -32
-346 -89 -366 -77 -14 9 -9 51 13 110 35 93 114 158 229 190 64 18 201 17 273
-2z m-1144 -25 c93 -29 121 -42 191 -83 41 -25 101 -69 133 -98 l58 -53 -24
-29 -24 -30 -92 23 c-51 12 -111 30 -134 40 l-41 18 44 11 c25 6 54 17 64 25
19 14 19 15 -3 51 -28 44 -45 45 -155 12 l-80 -25 -55 21 c-31 11 -67 22 -81
25 -60 11 -70 14 -70 23 0 10 87 58 130 71 38 11 99 10 139 -2z m560 -20 c13
-23 11 -31 -18 -93 -32 -65 -33 -67 -52 -50 -10 9 -19 23 -19 31 0 7 -6 12
-12 11 -27 -6 -11 63 23 98 38 39 57 40 78 3z m-4524 -16 c-4 -10 -9 -50 -12
-90 l-6 -71 -82 -41 c-95 -47 -189 -135 -258 -241 -33 -52 -48 -66 -71 -68
l-28 -4 4 104 c3 90 7 111 35 170 17 37 52 89 77 116 74 79 204 139 305 141
37 1 42 -1 36 -16z m580 -73 c91 -43 245 -192 245 -237 0 -13 -65 -48 -143
-77 l-64 -25 -27 28 c-24 25 -29 41 -36 117 -5 49 -15 103 -23 119 -17 34 -31
105 -21 105 3 0 34 -13 69 -30z m3173 -103 c13 -10 17 -77 5 -77 -18 1 -127
66 -136 81 -6 9 -7 24 -4 33 6 14 12 14 64 -5 32 -12 64 -26 71 -32z m-1158
20 c19 -13 64 -39 100 -59 36 -19 121 -69 190 -110 111 -67 169 -100 231 -133
11 -5 19 -13 19 -17 0 -5 -344 -8 -765 -8 -421 0 -765 3 -765 8 0 7 65 52 76
52 4 0 43 22 88 48 301 180 375 222 387 222 11 0 14 -17 14 -68 0 -58 4 -75
28 -110 36 -55 95 -85 168 -85 82 0 158 53 189 131 12 31 10 98 -5 135 -10 23
4 21 45 -6z m2554 -99 c-1 -24 -2 -61 -3 -82 l-1 -40 -27 26 c-16 14 -49 39
-75 57 -27 18 -48 36 -48 40 0 20 140 65 151 49 3 -4 4 -27 3 -50z m-662 -39
c28 -15 59 -91 60 -147 0 -61 -26 -125 -64 -158 -26 -21 -39 -24 -82 -22 -44
3 -54 0 -73 -22 l-22 -25 -1 31 c0 49 56 261 80 299 33 53 62 65 102 44z
m-4502 -32 c-4 -12 -12 -21 -17 -20 -5 1 -9 -7 -9 -18 0 -10 5 -19 12 -19 6 0
14 -17 18 -37 9 -60 7 -271 -4 -278 -5 -3 -28 4 -50 15 l-41 21 6 92 c7 103
24 175 37 155 5 -8 8 2 8 25 0 35 -2 38 -22 31 -20 -6 -21 -5 -9 10 11 13 11
16 0 16 -8 1 2 9 21 19 42 23 62 18 50 -12z m4949 -32 c61 -28 120 -79 156
-136 26 -40 51 -116 42 -125 -3 -3 -38 19 -78 50 -116 91 -264 155 -360 156
-33 0 -37 3 -43 32 -7 37 -7 38 36 49 60 15 185 2 247 -26z m-693 -52 c-13
-27 -26 -73 -30 -104 -7 -51 -11 -59 -71 -117 -52 -50 -74 -81 -114 -164 -27
-57 -57 -134 -67 -173 -9 -38 -20 -74 -24 -78 -4 -5 -19 29 -34 75 -22 68 -28
104 -29 197 l-2 115 40 27 c22 16 58 37 80 49 126 63 140 83 89 122 -13 11
-24 23 -24 27 0 5 26 20 58 33 78 35 82 36 120 37 l32 1 -24 -47z m-4456 -148
l0 -85 -62 1 c-58 0 -132 16 -85 18 9 1 35 19 57 41 22 22 45 40 50 40 6 0 10
4 10 9 0 15 19 61 25 61 3 0 5 -38 5 -85z m892 -24 c3 9 10 7 25 -8 12 -12 24
-19 27 -16 3 3 31 -9 61 -28 l56 -34 -3 -125 c-3 -96 -8 -134 -22 -165 l-19
-40 -14 45 c-7 25 -15 54 -17 65 -6 32 -55 157 -67 172 -6 7 -9 20 -5 28 4 11
2 14 -6 9 -8 -5 -9 -2 -5 10 4 10 3 15 -3 11 -6 -3 -10 -3 -11 2 -3 28 -7 51
-14 68 -5 14 -4 16 3 6 8 -11 10 -11 14 0z m3034 -27 l42 -16 7 -92 c3 -50 5
-269 3 -486 l-3 -395 -1394 2 c-766 1 -1395 4 -1397 5 -2 3 -7 751 -5 915 l1
72 43 4 c23 2 631 4 1352 5 1180 2 1313 0 1351 -14z m1245 -23 c56 -37 98 -82
83 -88 -7 -2 -42 -22 -78 -44 -37 -22 -70 -38 -75 -35 -5 3 -16 -3 -26 -14
-10 -11 -24 -20 -32 -20 -7 0 -13 -4 -13 -9 0 -11 -151 -14 -168 -3 -9 6 -12
37 -10 118 l3 109 67 0 c36 0 69 -3 73 -6 3 -4 10 -30 14 -59 5 -29 14 -56 20
-60 7 -4 13 -21 13 -38 1 -18 3 -32 5 -32 2 0 17 12 33 27 28 25 30 30 30 105
0 43 4 78 8 78 5 0 29 -13 53 -29z m-4672 -161 l0 -105 -35 39 c-35 36 -36 41
-30 89 7 50 18 80 40 103 18 20 25 -12 25 -126z m-359 6 l95 -32 3 -130 c2
-71 0 -166 -3 -211 l-7 -82 -52 52 c-28 29 -76 65 -106 81 -30 16 -76 47 -101
68 -25 21 -49 38 -53 38 -5 0 -26 15 -49 32 -31 25 -51 33 -85 33 -41 1 -47 5
-78 48 -19 26 -34 50 -34 55 0 11 50 39 102 58 113 41 227 38 368 -10z m4550
-14 c0 -60 -11 -82 -42 -82 -15 0 -18 8 -18 44 0 61 15 96 40 96 18 0 20 -6
20 -58z m905 18 c30 -19 35 -19 116 -4 81 16 260 17 275 2 16 -17 -87 -431
-116 -462 -5 -4 -25 -3 -46 4 -21 7 -69 13 -107 13 -58 0 -69 3 -79 20 -22 43
-104 120 -153 144 -90 46 -215 42 -287 -9 -25 -17 -29 -17 -67 -2 -47 19 -51
36 -21 101 25 56 93 123 155 152 38 19 70 25 130 27 45 1 95 9 115 18 45 20
47 20 85 -4z m-6235 -1 c120 -27 244 -116 300 -215 27 -46 36 -54 61 -54 26 0
33 -6 50 -44 10 -24 22 -59 25 -76 6 -28 10 -31 33 -25 14 3 56 9 93 12 56 4
75 2 112 -17 51 -24 93 -68 103 -108 3 -15 28 -49 55 -75 l49 -49 -3 -71 -3
-72 -138 -3 c-134 -2 -138 -2 -128 17 16 30 13 108 -5 147 -10 21 -34 45 -61
60 l-43 26 -53 -21 c-78 -31 -101 -31 -105 -1 -12 119 -85 217 -200 272 -56
27 -71 30 -130 26 -40 -3 -84 -14 -108 -26 l-42 -21 -16 57 c-20 74 -46 209
-46 245 l0 27 78 0 c42 0 97 -5 122 -11z m1363 -74 c90 -48 97 -58 97 -148 0
-33 -3 -33 -120 17 l-75 31 -3 73 c-2 40 1 72 6 72 6 0 48 -20 95 -45z m4270
-85 c-13 -87 -27 -122 -52 -131 -14 -5 -39 -15 -54 -24 l-28 -15 3 73 c3 62 5
72 21 69 9 -2 17 2 17 9 0 7 11 10 29 7 17 -2 30 -2 29 1 -2 22 4 32 20 29 9
-2 16 -10 15 -18z m-308 -181 c0 -118 -2 -140 -18 -157 -10 -11 -28 -22 -39
-25 -20 -6 -20 -3 -14 96 4 56 9 130 12 165 6 61 7 63 33 60 l26 -3 0 -136z
m-4181 119 c10 -31 15 -278 7 -278 -6 0 -23 12 -38 26 -27 25 -28 31 -34 137
-3 62 -4 115 -2 120 7 12 63 8 67 -5z m408 -187 c48 -23 105 -47 125 -54 l38
-12 3 -80 c4 -99 -4 -145 -24 -145 -8 0 -64 34 -124 76 -61 41 -152 99 -203
128 l-92 52 -3 82 -3 81 98 -43 c54 -24 137 -62 185 -85z m3594 73 c-3 -9 -6
-39 -6 -67 l-1 -52 -77 -35 c-42 -19 -135 -74 -207 -122 l-130 -86 -3 106 c-3
120 0 126 63 117 35 -5 45 -2 65 20 13 14 27 25 31 25 4 0 61 25 126 55 127
58 149 64 139 39z m930 -30 c57 -27 154 -150 154 -195 0 -18 -93 -103 -110
-100 -8 1 -53 22 -100 45 -93 46 -161 69 -170 58 -3 -4 -36 -8 -75 -10 -43 -2
-82 -10 -100 -21 -45 -26 -79 -95 -79 -158 l1 -53 -42 0 c-30 0 -45 5 -49 16
-3 9 -6 81 -6 160 l0 144 36 40 c62 69 160 85 251 42 30 -14 37 -14 56 -2 83
53 166 66 233 34z m-4914 -315 c14 -121 8 -139 -46 -125 -21 5 -24 13 -31 87
-7 89 -3 99 44 95 23 -3 27 -8 33 -57z m4158 29 c0 -13 3 -51 5 -85 l4 -63
-44 0 c-44 0 -45 1 -45 33 0 17 3 56 6 85 7 51 7 52 40 52 28 0 34 -4 34 -22z
m1040 -263 c0 -22 -179 -337 -259 -455 l-30 -44 21 -23 c21 -23 22 -23 330
-23 257 0 310 -2 314 -14 11 -28 -36 -253 -76 -371 -69 -201 -171 -378 -312
-541 -269 -312 -664 -512 -1093 -554 -110 -10 -868 -11 -1080 0 -60 3 -200 -1
-310 -8 -278 -19 -935 -21 -1150 -3 -93 8 -235 12 -315 10 -80 -2 -392 -4
-695 -4 -628 0 -658 3 -894 81 -442 146 -774 430 -976 833 -68 137 -132 344
-153 497 l-8 61 65 7 c36 3 186 6 332 6 253 0 267 1 284 20 18 19 16 23 -57
132 -116 174 -192 305 -218 373 l-10 25 3145 0 c1730 0 3145 -2 3145 -5z"/>
<path d="M4825 8594 c-16 -2 -79 -9 -140 -15 -309 -30 -687 -126 -921 -234
-43 -20 -101 -46 -128 -58 -28 -12 -81 -38 -117 -59 -36 -21 -69 -38 -72 -38
-16 0 -304 -180 -358 -224 -14 -12 -41 -32 -59 -46 -18 -14 -44 -35 -57 -48
-12 -12 -25 -22 -29 -21 -12 3 -94 -72 -89 -82 3 -5 0 -6 -7 -4 -11 5 -251
-222 -335 -316 -21 -23 -21 -25 -4 -25 12 0 17 5 13 15 -3 9 -1 12 6 7 7 -4
12 -2 12 6 0 9 3 9 10 -2 7 -12 10 -8 10 15 1 28 1 29 15 11 14 -19 15 -19 21
0 11 27 26 35 43 21 12 -10 14 -9 8 7 -6 14 -4 17 9 12 12 -4 15 -2 11 9 -8
20 13 76 25 69 6 -4 6 -10 -1 -17 -19 -19 -12 -35 20 -51 28 -14 30 -14 25 0
-5 14 14 44 28 44 10 0 6 -36 -5 -47 -8 -8 -8 -16 0 -30 10 -17 10 -17 12 2 1
11 1 23 1 26 -1 4 10 6 23 5 14 0 25 -6 25 -12 0 -21 45 -7 57 17 7 13 18 24
25 24 14 1 12 24 -3 40 -6 6 -12 2 -15 -13 -4 -12 -13 -22 -21 -22 -8 0 -11 5
-7 11 3 6 0 15 -7 20 -7 4 -10 12 -5 16 5 4 11 2 13 -4 8 -21 20 -15 28 14 4
19 9 23 14 14 6 -10 13 -7 25 10 l17 24 -7 -27 c-10 -43 13 -34 24 10 7 25 10
30 11 15 1 -13 6 -23 12 -23 8 0 7 -6 -2 -17 -13 -17 -13 -17 5 -3 51 39 78
69 72 79 -5 7 -1 9 8 5 9 -3 16 -1 16 4 0 6 10 14 21 17 29 9 139 94 139 106
0 6 4 8 9 5 8 -5 69 35 80 53 4 5 13 11 21 13 8 2 21 10 28 18 11 12 12 12 6
1 -4 -8 12 -1 37 16 81 57 224 134 244 131 13 -2 21 -12 23 -28 3 -26 1 -28
-118 -93 -116 -63 -200 -119 -193 -130 3 -5 1 -7 -5 -3 -19 12 -227 -138 -216
-156 4 -7 2 -8 -4 -4 -13 8 -74 -42 -67 -54 3 -4 -3 -7 -13 -6 -10 0 -17 -6
-17 -16 0 -10 -6 -23 -14 -30 -12 -11 -13 -10 -7 6 5 15 4 17 -7 8 -16 -14
-16 -38 2 -70 13 -24 36 -20 27 4 -6 15 11 18 38 8 9 -3 13 -10 10 -15 -3 -5
-9 -7 -14 -4 -4 3 -10 -2 -14 -10 -8 -21 0 -19 53 12 2 2 -8 12 -22 24 -30 23
-34 36 -13 36 8 0 20 -11 27 -24 16 -29 21 -29 40 3 l16 27 -1 -32 c-1 -20 -5
-30 -13 -27 -7 3 -15 1 -18 -4 -3 -5 4 -11 15 -15 11 -3 20 -11 20 -16 0 -5 5
-9 10 -9 6 0 10 6 10 14 0 8 6 17 13 19 7 3 5 6 -5 6 -10 1 -18 6 -18 12 0 6
9 9 20 6 11 -3 20 -1 20 4 0 4 -9 13 -20 19 -11 6 -20 15 -20 20 0 18 20 10
42 -15 16 -19 24 -22 30 -13 5 9 8 8 8 -4 0 -10 -7 -18 -15 -18 -14 0 -35 -29
-35 -48 0 -6 6 -12 14 -15 11 -4 14 1 13 21 -2 19 3 27 18 30 11 2 23 9 27 16
6 8 8 7 8 -2 0 -9 8 -11 23 -8 12 3 16 3 10 0 -19 -8 -16 -24 2 -18 10 4 13
13 10 24 -3 10 -1 21 5 25 16 10 25 -25 11 -46 -6 -11 -7 -19 -2 -19 17 0 30
27 26 51 -5 26 12 79 26 79 4 0 11 -4 14 -10 3 -5 -1 -10 -10 -10 -9 0 -14 -4
-10 -9 3 -5 1 -13 -5 -16 -8 -5 -8 -11 -1 -19 6 -7 7 -16 3 -21 -4 -4 4 -1 18
6 14 8 27 17 30 20 3 3 21 14 40 25 19 10 39 25 43 32 4 6 13 12 18 12 6 0 34
15 62 34 29 19 64 40 80 47 15 7 27 16 27 21 0 4 9 8 21 8 12 0 17 4 14 11 -4
6 -1 9 6 8 8 -2 52 16 98 39 46 23 88 42 93 42 5 0 28 8 51 19 67 29 81 34 91
32 4 -1 13 3 20 8 12 10 176 61 281 87 33 8 67 19 76 24 9 4 61 13 115 20 54
6 137 18 183 26 46 8 124 14 172 14 l89 0 1 218 c1 119 1 220 1 223 -2 12 43
-3 56 -19 9 -12 12 -72 12 -221 0 -120 4 -200 9 -192 5 8 10 9 12 3 4 -12 135
-19 146 -9 3 4 13 1 21 -6 12 -9 16 -9 19 1 5 14 33 17 33 2 0 -5 6 -7 14 -4
8 3 17 0 21 -5 3 -6 11 -8 17 -5 6 4 14 1 18 -6 5 -8 33 -13 78 -14 39 0 68
-4 67 -7 -6 -8 131 -28 158 -23 19 4 20 3 3 -4 -19 -8 -19 -9 2 -14 12 -4 24
-2 28 3 3 5 17 1 31 -9 15 -9 36 -15 46 -14 12 2 17 -1 13 -7 -5 -8 14 -11 58
-11 54 0 64 -3 60 -15 -6 -15 9 -20 49 -17 9 1 17 -5 17 -14 0 -10 6 -14 14
-11 8 3 16 2 18 -4 2 -5 21 -12 43 -15 22 -4 46 -14 53 -22 8 -11 28 -16 56
-16 32 0 42 -4 39 -13 -3 -7 0 -13 6 -13 6 0 11 6 11 13 0 9 3 8 9 -2 6 -9 10
-10 16 -2 5 9 10 9 20 1 7 -6 19 -8 28 -4 8 3 18 1 22 -5 3 -7 -2 -11 -14 -11
-11 0 -22 -4 -25 -8 -6 -10 35 -9 51 1 17 11 63 -21 56 -39 -4 -10 3 -14 23
-15 16 0 23 -3 16 -6 -16 -6 3 -33 23 -33 8 0 16 -6 18 -12 5 -12 11 16 8 34
0 4 9 13 22 19 18 9 20 9 10 -2 -19 -19 -17 -69 3 -69 11 0 14 6 10 23 -3 12
-3 17 0 10 3 -7 12 -9 20 -6 8 3 14 0 14 -6 0 -6 -5 -11 -11 -11 -5 0 -7 -4
-4 -10 3 -5 13 -10 21 -10 8 0 13 4 10 9 -3 5 2 15 11 22 15 12 16 12 10 -3
-8 -22 6 -23 23 -3 7 8 17 15 22 15 6 0 0 -9 -13 -21 l-24 -21 22 5 c16 4 22
0 21 -12 -2 -30 2 -51 11 -51 4 0 7 18 5 40 -2 30 1 40 12 40 9 0 12 -5 9 -11
-4 -5 -4 -22 -1 -35 6 -21 9 -24 21 -14 11 9 18 9 28 -2 21 -21 31 -58 16 -58
-10 0 -10 -3 -2 -11 15 -15 34 -3 26 16 -6 17 22 21 32 5 3 -5 1 -10 -4 -10
-14 0 -14 -40 0 -60 8 -11 9 -7 4 18 -7 35 1 41 21 15 12 -16 13 -16 14 -1 0
9 -6 19 -12 21 -8 4 -4 8 9 12 12 4 24 14 26 24 3 14 5 13 12 -3 6 -13 4 -21
-3 -24 -14 -4 -16 -42 -3 -42 11 0 21 24 22 53 0 21 1 21 8 3 7 -18 8 -18 14
-2 4 9 11 14 17 11 18 -11 11 -30 -17 -48 l-28 -17 27 6 c18 4 33 1 43 -9 21
-22 20 -23 -24 -19 -36 4 -38 2 -45 -29 -8 -42 0 -50 9 -9 7 31 9 32 45 26 22
-3 41 -2 44 3 3 5 -3 26 -13 47 -44 89 -45 93 -33 119 7 15 17 23 23 20 6 -5
7 -11 0 -19 -5 -6 -7 -31 -4 -54 5 -37 9 -42 32 -42 15 0 34 -9 44 -20 14 -17
14 -20 2 -20 -8 0 -15 -4 -15 -8 0 -16 40 -6 56 14 8 10 12 13 9 6 -6 -12 -4
-12 16 -1 l24 14 -23 3 c-12 2 -20 7 -17 12 3 4 -2 13 -10 20 -13 11 -14 10
-9 -4 3 -9 2 -16 -4 -16 -12 0 -24 29 -17 40 3 5 0 12 -6 16 -8 4 -9 3 -5 -4
4 -7 0 -12 -11 -13 -10 0 -13 -3 -5 -6 6 -2 12 -11 12 -19 0 -12 -4 -12 -20
-2 -11 7 -20 18 -20 25 0 6 -6 14 -12 17 -7 3 -3 3 9 0 28 -6 25 17 -6 50 -20
21 -26 23 -42 13 -11 -7 -19 -20 -19 -29 0 -10 -4 -18 -8 -18 -10 0 -9 36 1
46 4 4 2 13 -4 21 -12 14 0 18 17 6 5 -5 -3 4 -19 19 -16 14 -80 60 -142 102
-78 53 -118 74 -131 70 -14 -4 -15 -3 -6 4 11 7 6 14 -22 31 -20 12 -41 19
-47 15 -7 -4 -9 -3 -5 4 4 6 -25 27 -74 52 -65 34 -80 47 -80 65 0 15 8 26 20
30 25 8 107 -22 114 -41 3 -8 17 -14 31 -14 14 0 25 -5 25 -11 0 -8 6 -7 17 2
10 8 14 9 10 2 -9 -14 29 -52 60 -59 13 -4 20 -11 16 -17 -4 -6 0 -8 10 -4 12
4 17 1 17 -9 0 -11 6 -14 16 -10 8 3 12 2 9 -4 -3 -5 6 -12 20 -16 13 -3 23
-10 20 -14 -3 -4 9 -13 25 -20 17 -7 30 -17 30 -22 0 -6 9 -8 20 -5 10 3 18 1
17 -3 -2 -10 100 -100 114 -100 5 0 9 5 9 10 0 6 5 10 10 10 7 0 7 -6 1 -19
-8 -14 -5 -21 14 -31 14 -7 25 -17 25 -22 0 -4 7 -8 15 -8 8 0 14 -6 13 -12
-2 -9 7 -12 25 -10 18 2 26 -1 22 -8 -6 -10 16 -40 30 -40 4 0 25 -18 47 -40
37 -39 58 -44 58 -14 0 18 17 18 37 -1 8 -8 19 -12 24 -9 6 3 22 3 37 -1 18
-4 22 -9 13 -14 -10 -7 -10 -12 0 -29 11 -17 10 -24 -5 -47 -10 -15 -15 -29
-12 -32 3 -3 8 2 12 11 3 9 13 16 21 16 8 0 21 6 29 14 19 20 51 9 59 -21 4
-19 9 -22 19 -14 21 17 -2 61 -32 61 -13 0 -21 4 -17 9 14 23 -15 18 -33 -5
-19 -27 -19 -27 -25 -5 -4 17 0 24 17 30 12 5 22 18 23 31 2 19 -2 22 -26 17
-16 -3 -31 -3 -35 0 -9 10 15 34 27 26 6 -4 8 0 4 10 -4 11 -2 14 8 11 8 -3
11 -12 9 -19 -3 -7 4 -16 15 -20 12 -3 21 -10 21 -15 0 -5 7 -7 15 -4 8 4 15
1 15 -5 0 -6 -7 -11 -15 -11 -22 0 -18 -17 4 -23 13 -3 22 1 24 12 4 13 6 11
12 -6 4 -13 12 -23 17 -23 5 0 6 -5 2 -12 -5 -8 -2 -9 11 -4 14 5 16 4 6 -7
-9 -11 -8 -17 2 -26 8 -6 16 -8 19 -5 3 2 8 -2 11 -11 5 -11 0 -15 -16 -15
-19 -1 -20 -2 -6 -10 12 -7 25 -6 42 3 l25 13 -24 23 c-13 12 -28 20 -33 17
-5 -3 -8 1 -7 9 1 18 -163 197 -175 189 -5 -3 -8 -2 -7 3 6 18 -166 169 -326
285 -214 157 -441 287 -716 411 -229 104 -558 192 -870 233 -108 14 -596 28
-665 18z m1902 -509 c0 -8 -4 -15 -9 -15 -10 0 -11 14 -1 23 9 10 10 9 10 -8z
m-177 -5 c0 -5 -5 -10 -11 -10 -5 0 -7 5 -4 10 3 6 8 10 11 10 2 0 4 -4 4 -10z
m-3040 -40 c0 -5 -2 -10 -4 -10 -3 0 -8 5 -11 10 -3 6 -1 10 4 10 6 0 11 -4
11 -10z m3210 1 c0 -6 -4 -13 -10 -16 -5 -3 -10 1 -10 9 0 9 5 16 10 16 6 0
10 -4 10 -9z m-120 -11 c0 -5 -2 -10 -4 -10 -3 0 -8 5 -11 10 -3 6 -1 10 4 10
6 0 11 -4 11 -10z m-3375 -20 c-3 -5 -12 -10 -18 -10 -7 0 -6 4 3 10 19 12 23
12 15 0z m3642 -36 c-3 -3 -12 -4 -19 -1 -8 3 -5 6 6 6 11 1 17 -2 13 -5z m48
-32 c-3 -3 -11 0 -18 7 -9 10 -8 11 6 5 10 -3 15 -9 12 -12z m-65 -33 c0 -14
-17 -10 -23 5 -4 10 -1 13 9 9 7 -3 14 -9 14 -14z m-850 7 c0 -3 -4 -8 -10
-11 -5 -3 -10 -1 -10 4 0 6 5 11 10 11 6 0 10 -2 10 -4z m945 -16 c3 -5 1 -10
-4 -10 -6 0 -11 5 -11 10 0 6 2 10 4 10 3 0 8 -4 11 -10z m19 -38 c-4 -18 -11
-32 -16 -32 -6 0 -7 8 -3 18 4 9 10 25 12 35 9 29 14 13 7 -21z m52 12 c-4 -9
-9 -15 -11 -12 -3 3 -3 13 1 22 4 9 9 15 11 12 3 -3 3 -13 -1 -22z m-3796 -24
c0 -5 -5 -10 -11 -10 -5 0 -7 5 -4 10 3 6 8 10 11 10 2 0 4 -4 4 -10z m600
-10 c0 -5 -4 -10 -10 -10 -5 0 -10 5 -10 10 0 6 5 10 10 10 6 0 10 -4 10 -10z
m3350 -15 c0 -8 -4 -15 -10 -15 -5 0 -7 7 -4 15 4 8 8 15 10 15 2 0 4 -7 4
-15z m-4170 -5 c0 -5 -4 -10 -10 -10 -5 0 -10 5 -10 10 0 6 5 10 10 10 6 0 10
-4 10 -10z m3200 0 c0 -5 -4 -10 -9 -10 -6 0 -13 5 -16 10 -3 6 1 10 9 10 9 0
16 -4 16 -10z m150 0 c12 -8 11 -10 -7 -10 -12 0 -25 5 -28 10 -8 13 15 13 35
0z m684 -59 c-2 -2 -13 4 -24 14 -11 10 -20 15 -20 11 0 -4 -5 -4 -10 -1 -6 4
-8 11 -4 16 3 5 18 -1 33 -13 16 -13 27 -25 25 -27z m-3984 25 c0 -3 -4 -8
-10 -11 -5 -3 -10 -1 -10 4 0 6 5 11 10 11 6 0 10 -2 10 -4z m3687 -18 c-3 -8
-6 -5 -6 6 -1 11 2 17 5 13 3 -3 4 -12 1 -19z m468 12 c-3 -5 -12 -10 -18 -10
-7 0 -6 4 3 10 19 12 23 12 15 0z m-54 -43 c-8 -8 -11 -7 -11 4 0 9 3 19 7 23
4 4 9 2 11 -4 3 -7 -1 -17 -7 -23z m-4058 8 c1 -5 -6 -11 -15 -13 -11 -2 -18
3 -18 13 0 17 30 18 33 0z m3922 -3 c-3 -3 -11 0 -18 7 -9 10 -8 11 6 5 10 -3
15 -9 12 -12z m-4130 -3 c11 -16 1 -19 -13 -3 -7 8 -8 14 -3 14 5 0 13 -5 16
-11z m89 -7 c3 -5 -1 -9 -9 -9 -8 0 -12 4 -9 9 3 4 7 8 9 8 2 0 6 -4 9 -8z
m46 -2 c0 -5 -2 -10 -4 -10 -3 0 -8 5 -11 10 -3 6 -1 10 4 10 6 0 11 -4 11
-10z m4080 0 c0 -5 -4 -10 -10 -10 -5 0 -10 5 -10 10 0 6 5 10 10 10 6 0 10
-4 10 -10z m135 0 c-3 -5 -11 -10 -16 -10 -6 0 -7 5 -4 10 3 6 11 10 16 10 6
0 7 -4 4 -10z m-370 -26 c-9 -9 -19 -13 -23 -10 -3 4 0 11 8 16 24 15 33 11
15 -6z m426 6 c5 0 4 -6 -3 -14 -9 -10 -17 -11 -25 -4 -18 15 -16 31 3 24 9
-3 20 -6 25 -6z m-671 -15 c-7 -9 -15 -13 -19 -10 -3 3 1 10 9 15 21 14 24 12
10 -5z m518 -6 c4 -11 2 -11 -8 -2 -7 6 -20 9 -29 6 -14 -4 -14 -3 -1 6 18 13
32 10 38 -10z m52 -3 c0 -16 -28 -42 -36 -33 -7 6 18 47 28 47 5 0 8 -6 8 -14z
m-4140 0 c0 -3 -4 -8 -10 -11 -5 -3 -10 -1 -10 4 0 6 5 11 10 11 6 0 10 -2 10
-4z m405 -6 c3 -5 2 -10 -4 -10 -5 0 -13 5 -16 10 -3 6 -2 10 4 10 5 0 13 -4
16 -10z m3293 -8 c-8 -9 -14 -9 -24 -1 -19 16 -18 17 10 15 18 -1 22 -4 14
-14z m74 -7 c3 -14 1 -25 -3 -25 -5 0 -9 11 -9 25 0 14 2 25 4 25 2 0 6 -11 8
-25z m-3992 11 c0 -3 -4 -8 -10 -11 -5 -3 -10 -1 -10 4 0 6 5 11 10 11 6 0 10
-2 10 -4z m4384 -20 c-3 -9 -10 -16 -15 -16 -5 0 -4 9 3 20 14 22 21 20 12 -4z
m-4364 0 c0 -7 -11 -16 -25 -18 -14 -3 -25 -1 -25 3 0 5 9 9 20 9 11 0 20 5
20 10 0 6 2 10 5 10 3 0 5 -6 5 -14z m30 4 c0 -5 -2 -10 -4 -10 -3 0 -8 5 -11
10 -3 6 -1 10 4 10 6 0 11 -4 11 -10z m695 0 c-3 -5 -13 -10 -21 -10 -8 0 -14
5 -14 10 0 6 9 10 21 10 11 0 17 -4 14 -10z m-795 -15 c-7 -8 -17 -15 -23 -15
-6 0 -2 7 9 15 25 19 30 19 14 0z m465 5 c3 -5 -1 -10 -9 -10 -9 0 -16 5 -16
10 0 6 4 10 9 10 6 0 13 -4 16 -10z m98 -42 c9 -6 9 -8 0 -8 -14 0 -33 32 -32
52 0 7 5 2 10 -12 6 -13 15 -28 22 -32z m3527 37 c0 -9 -6 -12 -15 -9 -8 4
-12 10 -9 15 8 14 24 10 24 -6z m265 5 c-3 -5 -11 -10 -16 -10 -6 0 -7 5 -4
10 3 6 11 10 16 10 6 0 7 -4 4 -10z m-3765 -4 c0 -2 -7 -6 -15 -10 -8 -3 -15
-1 -15 4 0 6 7 10 15 10 8 0 15 -2 15 -4z m98 -21 c-3 -3 -9 2 -12 12 -6 14
-5 15 5 6 7 -7 10 -15 7 -18z m3299 -1 c-9 -9 -28 6 -21 18 4 6 10 6 17 -1 6
-6 8 -13 4 -17z m525 19 c-10 -4 -10 -8 -1 -19 10 -12 9 -18 -5 -32 -16 -16
-17 -15 -10 13 6 29 6 29 -9 10 -11 -14 -16 -16 -17 -6 0 15 29 41 45 40 6 0
4 -3 -3 -6z m-4412 -13 c0 -5 -4 -10 -10 -10 -5 0 -10 5 -10 10 0 6 5 10 10
10 6 0 10 -4 10 -10z m550 1 c0 -5 -7 -12 -16 -15 -14 -5 -15 -4 -4 9 14 17
20 19 20 6z m-710 -22 c0 -6 -4 -7 -10 -4 -5 3 -10 11 -10 16 0 6 5 7 10 4 6
-3 10 -11 10 -16z m810 11 c0 -5 -7 -10 -15 -10 -8 0 -15 5 -15 10 0 6 7 10
15 10 8 0 15 -4 15 -10z m3870 -10 c0 -11 -4 -20 -9 -20 -5 0 -11 9 -14 20 -3
13 0 20 9 20 8 0 14 -9 14 -20z m-4610 1 c0 -5 -7 -14 -15 -21 -13 -10 -15 -9
-15 9 0 12 6 21 15 21 8 0 15 -4 15 -9z m385 -1 c3 -5 -1 -10 -9 -10 -9 0 -16
5 -16 10 0 6 4 10 9 10 6 0 13 -4 16 -10z m3643 -10 c-13 -20 -28 -27 -28 -12
0 10 22 32 32 32 5 0 3 -9 -4 -20z m-3350 -26 c-10 -10 -28 6 -28 24 0 15 1
15 17 -1 9 -9 14 -19 11 -23z m3442 20 c0 -8 -4 -12 -10 -9 -5 3 -10 10 -10
16 0 5 5 9 10 9 6 0 10 -7 10 -16z m-3673 -9 c18 -19 9 -33 -10 -16 -21 17
-77 3 -77 -20 0 -32 -18 -30 -23 4 -5 31 2 53 10 31 4 -13 53 -6 53 7 0 15 30
10 47 -6z m278 5 c3 -5 1 -10 -4 -10 -6 0 -11 5 -11 10 0 6 2 10 4 10 3 0 8
-4 11 -10z m3838 -4 c-3 -4 1 -12 8 -17 10 -6 8 -9 -9 -9 -15 0 -21 4 -16 12
5 8 2 9 -10 5 -20 -8 -39 0 -31 13 3 5 19 8 34 7 16 -1 27 -6 24 -11z m-4633
-11 c0 -8 -4 -15 -10 -15 -5 0 -7 7 -4 15 4 8 8 15 10 15 2 0 4 -7 4 -15z
m646 -10 c-3 -9 -11 -13 -16 -10 -8 5 -7 11 1 21 14 18 24 11 15 -11z m3884
11 c0 -9 7 -12 20 -9 24 6 27 -12 4 -21 -19 -7 -17 -8 -33 22 -8 14 -8 22 -1
22 5 0 10 -6 10 -14z m-4440 -6 c0 -5 7 -10 15 -10 8 0 15 -4 15 -9 0 -5 -11
-8 -24 -8 -18 0 -24 5 -23 18 1 19 17 27 17 9z m4065 0 c3 -5 -1 -10 -9 -10
-9 0 -16 5 -16 10 0 6 4 10 9 10 6 0 13 -4 16 -10z m-3448 -32 c-3 -8 -6 -5
-6 6 -1 11 2 17 5 13 3 -3 4 -12 1 -19z m-777 2 c0 -5 -2 -10 -4 -10 -3 0 -8
5 -11 10 -3 6 -1 10 4 10 6 0 11 -4 11 -10z m650 0 c0 -5 -5 -10 -11 -10 -5 0
-7 5 -4 10 3 6 8 10 11 10 2 0 4 -4 4 -10z m21 -23 c-8 -8 -11 -7 -11 4 0 20
13 34 18 19 3 -7 -1 -17 -7 -23z m-734 -29 c-3 -8 -6 -5 -6 6 -1 11 2 17 5 13
3 -3 4 -12 1 -19z"/>
<path d="M6384 7739 c-3 -6 -1 -16 5 -22 8 -8 11 -5 11 11 0 24 -5 28 -16 11z"/>
<path d="M6607 7615 c-17 -12 -16 -13 7 -11 25 1 34 10 18 20 -4 2 -15 -2 -25
-9z"/>
<path d="M2935 7589 c-11 -17 1 -21 15 -4 8 9 8 15 2 15 -6 0 -14 -5 -17 -11z"/>
<path d="M6715 7560 c3 -5 8 -10 11 -10 2 0 4 5 4 10 0 6 -5 10 -11 10 -5 0
-7 -4 -4 -10z"/>
<path d="M6746 7554 c-9 -24 -2 -26 12 -4 7 11 8 20 3 20 -5 0 -12 -7 -15 -16z"/>
<path d="M2987 7502 c1 -8 3 -16 3 -18 0 -2 7 -4 15 -4 8 0 15 5 15 10 0 6 -6
10 -14 10 -8 0 -16 3 -19 8 -2 4 -2 1 0 -6z"/>
<path d="M2700 7494 c0 -8 5 -12 10 -9 6 3 10 10 10 16 0 5 -4 9 -10 9 -5 0
-10 -7 -10 -16z"/>
<path d="M7020 7500 c0 -5 5 -10 11 -10 5 0 7 5 4 10 -3 6 -8 10 -11 10 -2 0
-4 -4 -4 -10z"/>
<path d="M7316 7501 c-14 -5 -16 -10 -7 -15 6 -4 20 -2 29 5 12 10 11 7 -3 -9
-16 -19 -17 -25 -6 -32 17 -10 63 9 55 22 -4 6 -11 5 -17 -1 -16 -16 -31 -13
-17 4 6 8 9 19 5 25 -7 11 -12 12 -39 1z"/>
<path d="M2666 7485 c-9 -26 -7 -32 5 -12 6 10 9 21 6 23 -2 3 -7 -2 -11 -11z"/>
<path d="M2736 7488 c4 -12 -1 -17 -18 -20 -16 -2 -19 -5 -8 -9 8 -4 23 -3 33
0 16 6 16 8 2 26 -11 15 -14 16 -9 3z"/>
<path d="M2781 7484 c0 -11 3 -14 6 -6 3 7 2 16 -1 19 -3 4 -6 -2 -5 -13z"/>
<path d="M7153 7493 c-7 -3 -13 -9 -13 -15 0 -6 7 -8 15 -4 8 3 15 3 15 0 0
-2 -10 -9 -22 -14 -22 -8 -22 -9 -2 -9 11 -1 25 -6 31 -12 7 -7 11 -3 11 15 0
28 -16 46 -35 39z"/>
<path d="M2944 7482 c-7 -4 -8 -15 -3 -27 4 -11 8 -15 9 -10 1 6 6 1 11 -10 8
-17 9 -16 3 5 -3 14 -6 31 -6 38 -1 6 -2 12 -2 12 -1 0 -6 -4 -12 -8z"/>
<path d="M6895 7470 c-3 -5 -1 -10 4 -10 6 0 11 5 11 10 0 6 -2 10 -4 10 -3 0
-8 -4 -11 -10z"/>
<path d="M3020 7465 c0 -5 5 -17 10 -25 5 -8 10 -10 10 -5 0 6 -5 17 -10 25
-5 8 -10 11 -10 5z"/>
<path d="M3275 7460 c-3 -5 3 -10 14 -10 12 0 21 5 21 10 0 6 -6 10 -14 10 -8
0 -18 -4 -21 -10z"/>
<path d="M2907 7452 c-5 -7 -1 -22 12 -37 10 -14 22 -21 25 -16 3 5 0 11 -8
14 -8 3 -16 16 -18 29 -2 16 -5 19 -11 10z"/>
<path d="M3114 7435 c1 -25 10 -32 20 -16 7 11 -3 41 -14 41 -4 0 -7 -11 -6
-25z"/>
<path d="M3150 7449 c0 -5 5 -7 10 -4 6 3 10 8 10 11 0 2 -4 4 -10 4 -5 0 -10
-5 -10 -11z"/>
<path d="M7026 7440 c-10 -11 -16 -26 -13 -35 9 -23 24 -18 23 7 -1 31 30 35
54 6 16 -18 19 -20 20 -6 1 49 -47 65 -84 28z"/>
<path d="M7200 7456 c0 -2 8 -10 18 -17 15 -13 16 -12 3 4 -13 16 -21 21 -21
13z"/>
<path d="M2620 7430 c0 -5 7 -10 16 -10 8 0 12 5 9 10 -3 6 -10 10 -16 10 -5
0 -9 -4 -9 -10z"/>
<path d="M2680 7425 c0 -8 5 -15 10 -15 6 0 10 7 10 15 0 8 -4 15 -10 15 -5 0
-10 -7 -10 -15z"/>
<path d="M3070 7430 c0 -5 7 -10 15 -10 8 0 15 5 15 10 0 6 -7 10 -15 10 -8 0
-15 -4 -15 -10z"/>
<path d="M6955 7430 c3 -5 10 -10 16 -10 5 0 9 5 9 10 0 6 -7 10 -16 10 -8 0
-12 -4 -9 -10z"/>
<path d="M2581 7410 c14 -31 19 -36 19 -24 0 6 -7 19 -16 30 -14 18 -14 18 -3
-6z"/>
<path d="M2870 7415 c-9 -11 -9 -15 -1 -15 7 0 9 -4 6 -10 -3 -5 -2 -10 3 -10
14 0 22 25 13 39 -6 9 -11 8 -21 -4z"/>
<path d="M3160 7415 c-6 -8 -10 -19 -8 -26 2 -6 9 0 16 15 13 29 10 33 -8 11z"/>
<path d="M7137 7394 c-30 -36 -31 -46 -1 -17 13 13 19 14 22 5 2 -6 8 -12 14
-12 7 0 6 5 -1 14 -6 7 -9 21 -5 30 9 23 3 19 -29 -20z"/>
<path d="M7450 7415 c0 -8 5 -15 10 -15 6 0 10 7 10 15 0 8 -4 15 -10 15 -5 0
-10 -7 -10 -15z"/>
<path d="M2991 7404 c0 -11 3 -14 6 -6 3 7 2 16 -1 19 -3 4 -6 -2 -5 -13z"/>
<path d="M3250 7410 c0 -5 7 -7 15 -4 8 4 15 8 15 10 0 2 -7 4 -15 4 -8 0 -15
-4 -15 -10z"/>
<path d="M7243 7408 c3 -9 1 -19 -6 -21 -7 -2 -9 -8 -5 -12 4 -4 14 -1 22 8
14 13 14 16 -1 29 -15 11 -16 11 -10 -4z"/>
<path d="M2475 7400 c3 -5 8 -10 11 -10 2 0 4 5 4 10 0 6 -5 10 -11 10 -5 0
-7 -4 -4 -10z"/>
<path d="M7058 7398 c5 -5 16 -8 23 -6 8 3 3 7 -10 11 -17 4 -21 3 -13 -5z"/>
<path d="M6938 7393 c7 -3 16 -2 19 1 4 3 -2 6 -13 5 -11 0 -14 -3 -6 -6z"/>
<path d="M6986 7387 c3 -10 9 -15 12 -12 3 3 0 11 -7 18 -10 9 -11 8 -5 -6z"/>
<path d="M7195 7390 c4 -6 11 -8 16 -5 14 9 11 15 -7 15 -8 0 -12 -5 -9 -10z"/>
<path d="M7415 7390 c-3 -5 -1 -10 4 -10 6 0 11 5 11 10 0 6 -2 10 -4 10 -3 0
-8 -4 -11 -10z"/>
<path d="M7470 7380 c0 -5 5 -10 10 -10 6 0 10 5 10 10 0 6 -4 10 -10 10 -5 0
-10 -4 -10 -10z"/>
<path d="M2896 7364 c-9 -24 -2 -26 12 -4 7 11 8 20 3 20 -5 0 -12 -7 -15 -16z"/>
<path d="M7057 7359 c7 -7 15 -10 18 -7 3 3 -2 9 -12 12 -14 6 -15 5 -6 -5z"/>
<path d="M7430 7360 c0 -5 5 -10 10 -10 6 0 10 5 10 10 0 6 -4 10 -10 10 -5 0
-10 -4 -10 -10z"/>
<path d="M7210 7350 c0 -5 5 -10 11 -10 5 0 7 5 4 10 -3 6 -8 10 -11 10 -2 0
-4 -4 -4 -10z"/>
<path d="M7590 7342 c0 -5 7 -16 16 -23 14 -12 16 -11 13 5 -4 20 -29 35 -29
18z"/>
<path d="M7680 7346 c0 -2 8 -10 18 -17 15 -13 16 -12 3 4 -13 16 -21 21 -21
13z"/>
<path d="M2790 7329 c0 -5 5 -7 10 -4 6 3 10 8 10 11 0 2 -4 4 -10 4 -5 0 -10
-5 -10 -11z"/>
<path d="M7309 7307 c6 -8 8 -17 4 -20 -3 -4 -2 -7 4 -7 18 0 22 12 8 26 -18
18 -31 18 -16 1z"/>
<path d="M7630 7280 c0 -5 4 -10 9 -10 6 0 13 5 16 10 3 6 -1 10 -9 10 -9 0
-16 -4 -16 -10z"/>
<path d="M7498 7273 c7 -3 16 -2 19 1 4 3 -2 6 -13 5 -11 0 -14 -3 -6 -6z"/>
<path d="M7770 7243 c0 -5 10 -18 23 -29 l22 -19 -20 25 c-11 14 -21 27 -22
29 -2 2 -3 0 -3 -6z"/>
<path d="M8057 5833 c-25 -25 -43 -52 -40 -59 2 -7 26 -15 52 -19 50 -7 171
-4 171 5 0 10 -115 120 -126 120 -6 0 -32 -21 -57 -47z m4 -56 c-10 -9 -11 -8
-5 6 3 10 9 15 12 12 3 -3 0 -11 -7 -18z"/>
<path d="M3274 5011 c20 -22 26 -25 26 -13 0 4 -10 13 -22 21 -23 14 -23 14
-4 -8z"/>
<path d="M7106 4745 c-9 -26 -7 -32 5 -12 6 10 9 21 6 23 -2 3 -7 -2 -11 -11z"/>
<path d="M7192 4720 c-18 -29 -15 -38 4 -12 9 13 14 25 12 27 -2 2 -9 -5 -16
-15z"/>
<path d="M6830 4749 c0 -5 5 -7 10 -4 6 3 10 8 10 11 0 2 -4 4 -10 4 -5 0 -10
-5 -10 -11z"/>
<path d="M5186 4178 c1 -128 3 -241 3 -250 1 -17 18 -18 216 -18 l215 0 0 250
0 250 -219 0 -218 0 3 -232z"/>
<path d="M3946 4139 c-4 -121 -3 -216 2 -221 5 -5 82 -7 173 -6 l164 3 3 218
2 217 -168 0 -169 0 -7 -211z"/>
<path d="M4502 4133 l3 -218 230 0 230 0 3 218 2 217 -235 0 -235 0 2 -217z"/>
<path d="M5842 4133 l3 -218 165 0 165 0 3 218 2 217 -170 0 -170 0 2 -217z
m236 0 l-3 -128 -67 -3 -68 -3 0 131 0 130 70 0 71 0 -3 -127z"/>
<path d="M3926 3175 l-37 -45 -516 -2 c-479 -3 -517 -4 -527 -20 -8 -13 -8
-23 0 -35 10 -17 47 -18 493 -21 264 -1 481 -5 481 -8 0 -8 -71 -95 -139 -170
-86 -94 -141 -165 -141 -181 0 -8 9 -28 21 -44 l20 -29 -119 0 c-101 0 -123
-3 -142 -18 -29 -23 -22 -67 12 -76 13 -3 299 -6 636 -6 599 0 612 0 632 20
26 26 25 45 -2 64 -19 14 -64 16 -289 16 -229 0 -266 2 -266 15 0 12 17 15 88
15 92 0 119 11 119 50 0 18 -78 228 -104 278 -7 15 -17 37 -20 50 l-7 22 140
0 c133 0 141 1 155 22 14 20 14 24 -1 40 -14 15 -37 18 -182 20 l-166 3 -23
43 c-33 59 -66 58 -116 -3z m27 -257 c-3 -95 -6 -174 -7 -175 -5 -6 -246 -6
-246 0 0 5 27 40 59 78 32 39 88 115 122 170 35 54 67 99 70 99 4 0 4 -78 2
-172z m146 -32 c54 -144 54 -146 -10 -146 l-50 0 0 58 c1 31 -1 104 -4 162 -6
120 -9 123 64 -74z m-151 -248 c-3 -9 -38 -14 -115 -16 -89 -2 -112 0 -123 13
-11 13 2 15 115 15 97 0 126 -3 123 -12z"/>
<path d="M5532 3118 c-18 -18 -14 -46 7 -58 13 -7 298 -10 855 -10 826 0 836
0 856 20 16 16 18 25 10 40 -11 20 -24 20 -863 20 -650 0 -856 -3 -865 -12z"/>
<path d="M7648 2785 c-32 -30 -58 -58 -58 -63 0 -5 7 -15 15 -22 13 -11 20 -9
40 10 l24 23 62 -57 62 -58 21 22 21 22 -59 53 c-57 51 -59 55 -47 79 14 25 8
46 -12 46 -7 -1 -38 -25 -69 -55z"/>
<path d="M2402 2734 c-40 -36 -72 -69 -72 -72 0 -4 7 -16 15 -26 14 -19 15
-18 36 7 30 39 39 33 32 -22 -5 -43 -3 -50 18 -65 23 -16 24 -15 27 1 10 60
12 63 47 63 24 0 38 7 49 22 27 39 20 76 -23 119 -21 22 -43 39 -48 39 -5 0
-41 -30 -81 -66z m108 -24 c12 -23 6 -40 -15 -40 -14 0 -35 29 -35 49 0 19 39
12 50 -9z"/>
<path d="M6262 2779 c-55 -28 -78 -60 -62 -88 14 -26 35 -26 88 -1 53 26 102
25 154 -1 65 -33 117 -5 84 46 -40 61 -181 85 -264 44z"/>
<path d="M7526 2671 c-22 -24 -21 -27 22 -57 l37 -26 -50 8 c-116 17 -121 2
-33 -96 66 -73 81 -81 97 -52 8 13 3 24 -22 50 -35 36 -27 40 49 21 39 -10 48
-9 62 5 15 15 12 21 -48 82 -81 82 -93 89 -114 65z"/>
<path d="M2605 2583 c-88 -95 -87 -90 -25 -144 43 -38 58 -46 72 -38 27 15 22
34 -17 60 -19 13 -35 29 -35 36 0 20 22 27 34 11 6 -8 21 -20 32 -26 18 -9 24
-8 34 4 11 12 8 20 -15 44 -21 22 -26 33 -18 41 7 7 21 2 46 -20 39 -35 49
-37 66 -17 9 11 0 24 -46 65 -32 28 -60 50 -63 50 -3 0 -32 -30 -65 -66z"/>
<path d="M5650 2607 c-27 -14 -36 -43 -20 -67 8 -13 86 -15 579 -18 510 -2
571 -1 585 13 20 21 20 49 0 69 -14 14 -79 16 -567 16 -424 0 -558 -3 -577
-13z"/>
<path d="M7308 2502 c-26 -20 -47 -41 -47 -47 -1 -5 29 -47 64 -93 74 -92 68
-91 145 -23 43 38 44 40 28 57 -17 17 -19 17 -47 -10 -18 -17 -36 -26 -45 -23
-23 9 -20 22 9 41 26 17 30 32 16 55 -7 11 -16 8 -45 -14 -32 -25 -36 -26 -43
-10 -4 13 3 25 26 44 23 19 30 32 25 44 -10 26 -34 20 -86 -21z"/>
<path d="M4940 2521 c-54 -17 -90 -42 -96 -68 -14 -53 27 -78 74 -44 49 34
101 37 162 8 41 -20 58 -23 72 -16 47 25 26 74 -46 108 -47 21 -117 27 -166
12z"/>
<path d="M2885 2444 c-11 -9 -51 -32 -90 -51 -38 -19 -72 -37 -74 -39 -2 -2 4
-13 14 -24 11 -13 25 -18 39 -14 30 7 74 -29 78 -64 2 -18 10 -28 24 -30 18
-3 23 7 43 103 17 83 19 110 10 121 -14 17 -19 17 -44 -2z m-15 -89 c0 -26
-14 -33 -25 -15 -9 14 1 40 15 40 5 0 10 -11 10 -25z"/>
<path d="M7156 2389 c-10 -16 -13 -36 -9 -70 3 -28 2 -49 -4 -49 -5 0 -24 11
-43 25 -38 28 -53 31 -68 12 -8 -10 0 -31 32 -86 24 -40 51 -80 60 -89 14 -15
17 -15 32 -1 14 14 13 19 -6 52 -26 43 -17 48 21 11 37 -36 53 -24 44 35 l-7
46 26 -24 c14 -14 26 -30 26 -38 0 -19 14 -16 34 6 20 22 25 14 -62 124 -30
37 -55 67 -57 67 -2 0 -11 -10 -19 -21z"/>
<path d="M3023 2273 c-28 -43 -54 -83 -57 -90 -9 -16 98 -87 119 -80 25 10 17
35 -19 60 l-35 23 41 67 c39 64 44 97 16 97 -8 0 -36 -35 -65 -77z"/>
<path d="M4430 2330 c-24 -24 -24 -30 -6 -55 13 -18 39 -18 652 -17 593 1 640
3 651 19 17 23 16 30 -7 53 -20 20 -33 20 -645 20 -612 0 -625 0 -645 -20z"/>
<path d="M6893 2243 c-30 -6 -63 -49 -63 -83 0 -19 8 -33 26 -45 22 -14 33
-15 72 -5 30 7 48 8 55 1 14 -14 -10 -41 -37 -41 -31 0 -50 -16 -43 -34 8 -20
58 -21 96 -1 16 8 34 28 41 44 25 61 -34 105 -112 84 -43 -12 -51 -8 -37 18 5
11 21 19 35 19 28 0 44 28 23 41 -15 9 -19 9 -56 2z"/>
<path d="M3432 2127 c-16 -18 -82 -160 -82 -174 0 -15 43 -29 47 -16 12 35 28
43 61 31 27 -11 37 -10 60 2 34 20 49 61 34 94 -15 33 -106 81 -120 63z m63
-87 c0 -18 -6 -26 -22 -28 -24 -3 -29 11 -17 43 10 25 39 14 39 -15z"/>
<path d="M6659 2111 c-34 -34 -37 -70 -9 -96 16 -14 30 -17 70 -12 29 4 52 2
56 -4 10 -16 -16 -38 -49 -41 -39 -4 -43 -29 -6 -42 36 -12 93 17 109 55 23
56 -28 95 -114 87 -45 -4 -43 19 3 33 42 12 53 32 25 43 -32 12 -56 5 -85 -23z"/>
<path d="M3631 2027 c-5 -12 -23 -56 -40 -97 -28 -69 -29 -76 -14 -87 25 -19
33 -16 45 19 10 29 12 30 25 13 7 -11 13 -28 13 -40 0 -26 18 -45 43 -45 17 0
18 5 13 35 -6 31 -3 40 23 64 55 51 35 104 -52 140 l-48 21 -8 -23z m79 -61
c0 -2 3 -11 6 -19 6 -17 -19 -29 -41 -21 -8 4 -15 15 -15 25 0 14 7 19 25 19
14 0 25 -2 25 -4z"/>
<path d="M6445 2015 c-58 -57 -15 -122 71 -109 41 6 46 5 42 -12 -2 -13 -16
-21 -46 -27 -33 -6 -42 -13 -40 -25 2 -12 15 -18 46 -20 36 -3 47 1 72 27 36
35 38 60 7 89 -18 17 -36 22 -75 22 -29 0 -52 4 -52 10 0 13 34 30 59 30 14 0
21 6 21 20 0 31 -73 28 -105 -5z"/>
<path d="M5928 2003 c7 -3 16 -2 19 1 4 3 -2 6 -13 5 -11 0 -14 -3 -6 -6z"/>
<path d="M5808 1973 c7 -3 16 -2 19 1 4 3 -2 6 -13 5 -11 0 -14 -3 -6 -6z"/>
<path d="M6257 1950 c-32 -10 -61 -21 -64 -24 -4 -4 54 -194 63 -204 5 -7 144
42 144 51 0 4 -5 17 -10 28 -11 19 -11 19 -50 -1 -49 -25 -50 -25 -50 1 0 13
10 23 30 30 19 7 30 18 30 29 0 28 -16 33 -49 15 -37 -19 -37 -19 -45 0 -4 12
7 21 40 35 32 14 45 25 42 37 -4 24 -16 24 -81 3z"/>
<path d="M3839 1911 c-77 -77 2 -215 104 -182 67 22 98 84 73 145 -19 45 -52
66 -104 66 -35 0 -49 -6 -73 -29z m115 -37 c23 -22 20 -60 -6 -84 -26 -24 -41
-25 -62 -5 -25 25 -29 54 -12 80 19 29 57 33 80 9z"/>
<path d="M4738 1903 c6 -2 18 -2 25 0 6 3 1 5 -13 5 -14 0 -19 -2 -12 -5z"/>
<path d="M4848 1893 c12 -2 30 -2 40 0 9 3 -1 5 -23 4 -22 0 -30 -2 -17 -4z"/>
<path d="M5263 1893 c9 -2 23 -2 30 0 6 3 -1 5 -18 5 -16 0 -22 -2 -12 -5z"/>
<path d="M4100 1851 c-27 -103 -38 -167 -31 -174 17 -17 46 -2 49 25 3 26 5
27 45 22 53 -7 87 20 87 69 0 51 -21 68 -99 86 l-41 9 -10 -37z m85 -35 c25
-18 13 -46 -20 -46 -25 0 -31 13 -19 44 7 20 15 20 39 2z"/>
<path d="M5993 1868 c-31 -35 -34 -45 -22 -72 14 -29 59 -50 95 -43 16 3 27 0
31 -10 8 -21 -4 -28 -50 -28 -55 0 -64 -28 -14 -44 60 -20 108 4 122 61 11 42
-31 78 -90 78 -57 0 -58 22 -2 31 44 7 51 13 44 34 -10 25 -89 20 -114 -7z"/>
<path d="M5776 1818 c-35 -33 -40 -60 -15 -91 17 -22 29 -27 65 -27 31 0 44
-4 44 -14 0 -17 -22 -26 -60 -26 -36 0 -49 -19 -25 -37 33 -23 83 -16 116 16
16 16 29 38 29 49 0 31 -57 73 -94 70 -22 -2 -31 1 -31 12 0 10 12 16 33 18
36 4 54 28 31 43 -25 16 -67 10 -93 -13z"/>
<path d="M4307 1759 c-32 -150 -35 -134 23 -147 79 -18 100 -16 100 11 0 19
-7 25 -42 33 -60 13 -59 40 0 35 41 -2 43 -1 40 21 -2 18 -10 24 -35 26 -26 3
-33 8 -33 24 0 18 4 20 33 13 54 -12 61 -11 65 9 6 27 -7 34 -74 41 l-61 7
-16 -73z"/>
<path d="M4515 1789 c-2 -8 -11 -54 -19 -104 -12 -70 -13 -91 -3 -97 28 -18
47 -1 47 43 0 32 16 21 33 -21 12 -32 20 -40 41 -40 26 0 36 23 16 35 -16 10
-11 41 10 60 29 26 27 90 -2 109 -34 22 -117 32 -123 15z m83 -48 c21 -13 10
-46 -16 -49 -24 -4 -38 18 -28 43 6 17 24 19 44 6z"/>
<path d="M5561 1753 c-25 -92 -40 -167 -35 -175 10 -15 43 -8 54 12 16 30 54
36 78 12 19 -19 62 -21 62 -4 0 4 -25 48 -56 99 -64 105 -87 118 -103 56z m57
-76 c2 -10 -3 -17 -12 -17 -10 0 -16 9 -16 21 0 24 23 21 28 -4z"/>
<path d="M4727 1744 c-4 -16 -9 -64 -13 -106 l-6 -78 30 0 c28 0 31 3 34 38
l3 37 22 -41 c23 -43 43 -57 68 -48 12 5 11 12 -5 45 -20 38 -20 38 0 49 15 8
20 21 20 49 0 50 -22 69 -92 77 -56 6 -56 6 -61 -22z m101 -51 c3 -17 -2 -23
-15 -23 -25 0 -43 19 -36 37 9 22 48 11 51 -14z"/>
<path d="M5298 1748 c-8 -13 -18 -32 -22 -43 l-7 -20 -15 20 c-8 11 -20 28
-27 39 -9 13 -19 17 -35 12 -12 -4 -22 -11 -22 -14 0 -4 18 -31 40 -61 31 -41
40 -62 40 -92 0 -37 2 -39 30 -39 29 0 30 1 29 49 -1 33 7 67 24 104 21 47 23
56 10 61 -24 10 -30 7 -45 -16z"/>
<path d="M4943 1747 c-11 -18 9 -47 33 -47 23 0 24 -2 24 -80 l0 -80 30 0 30
0 0 86 c0 75 2 85 16 80 19 -7 44 10 44 29 0 10 -24 14 -86 17 -47 2 -88 0
-91 -5z"/>
<path d="M6320 1620 c-23 -7 -23 -8 -3 -9 12 -1 25 4 28 9 3 6 5 10 3 9 -2 -1
-14 -5 -28 -9z"/>
<path d="M4165 1526 c17 -7 53 -16 80 -19 l50 -5 -44 14 c-25 7 -61 16 -80 19
l-36 5 30 -14z"/>
<path d="M6020 1530 c-21 -7 -21 -8 -5 -9 11 0 27 4 35 9 18 11 5 11 -30 0z"/>
<path d="M5958 1513 c6 -2 18 -2 25 0 6 3 1 5 -13 5 -14 0 -19 -2 -12 -5z"/>
</g>
</svg>

After

Width:  |  Height:  |  Size: 40 KiB

View File

@ -3,6 +3,8 @@ import 'package:equatable/equatable.dart';
import 'package:unit2/model/passo/city.dart';
import 'package:unit2/sevices/offline/offline_passo/admin/sql_services/sql_services.dart';
import '../../../../../sevices/offline/offline_passo/admin/api_services/municipalities_api_services.dart';
part 'municipalities_admin_event.dart';
part 'municipalities_admin_state.dart';
@ -15,6 +17,28 @@ class MunicipalitiesAdminBloc
emit(MunicipalitiesLoaded(city: city));
});
// on<MunicipalitiesSyncToDevice>((event, emit) async {
// try {
// final result =
// await MunicipalityAdminApiServices.instance.fetch();
// // Assuming result is a List of JSON objects, convert them to City objects.
// final cities =
// result.map((json) => City.fromJson(json)).toList();
// // Loop through the list of City objects and insert them into the local database.
// for (City city in cities) {
// print(city.cityDescription);
// print(city.cityCode);
// await SQLServices.instance.createMunicipalities(city);
// }
// } catch (e) {
// // Handle any errors that might occur during the API call or database insertion.
// print("Error: $e");
// }
// // emit(const LoadMunicipalities());
// });
on<AddMunicipality>((event, emit) async {
await SQLServices.instance.createMunicipalities(
City(

View File

@ -32,3 +32,10 @@ class LoadMunicipalities extends MunicipalitiesAdminEvent {
@override
List<Object> get props => [];
}
class MunicipalitiesSyncToDevice extends MunicipalitiesAdminEvent {
const MunicipalitiesSyncToDevice();
@override
List<Object> get props => [];
}

View File

@ -32,6 +32,7 @@ class BldgAssessmentOfflineBloc
recommendapprName: event.recommendapprName,
recommendapprDate: event.recommendapprDate,
approvedbyName: event.approvedbyName,
approvedbyDate: event.approvedbyDate,
memoranda: event.memoranda,
swornstatementNo: event.swornstatementNo,
dateReceived: event.dateReceived,

View File

@ -27,6 +27,7 @@ class AddBldgAssessment extends BldgAssessmentOfflineEvent {
final String recommendapprName;
final String recommendapprDate;
final String approvedbyName;
final String approvedbyDate;
final String memoranda;
final String swornstatementNo;
final String dateReceived;
@ -58,6 +59,7 @@ class AddBldgAssessment extends BldgAssessmentOfflineEvent {
required this.recommendapprName,
required this.recommendapprDate,
required this.approvedbyName,
required this.approvedbyDate,
required this.memoranda,
required this.swornstatementNo,
required this.dateReceived,
@ -91,6 +93,7 @@ class AddBldgAssessment extends BldgAssessmentOfflineEvent {
recommendapprName,
recommendapprDate,
approvedbyName,
approvedbyDate,
memoranda,
swornstatementNo,
dateReceived,

View File

@ -1,9 +1,12 @@
import 'dart:convert';
import 'dart:io';
import 'package:bloc/bloc.dart';
import 'package:equatable/equatable.dart';
import 'package:intl/intl.dart';
import 'package:unit2/model/passo/floor_sketch.dart';
import 'package:unit2/sevices/offline/offline_passo/admin/sql_services/sql_services.dart';
import 'package:unit2/sevices/passo/building/building_services.dart';
import '../../../../../model/offline/offline_profile.dart';
import '../../../../../model/passo/additional_items.dart';
import '../../../../../model/passo/bldg_loc.dart';
@ -14,9 +17,13 @@ import '../../../../../model/passo/property_assessment.dart';
import '../../../../../model/passo/property_info.dart';
import '../../../../../model/passo/structureMaterial.dart';
import '../../../../../model/passo/todo.dart';
import '../../../../../model/profile/basic_information/primary-information.dart';
import '../../../../../sevices/offline/offline_passo/building/property_owner_info_service.dart';
import 'package:http/http.dart';
import 'package:path/path.dart';
// as http;
import '../../../../../utils/urls.dart';
part 'crud_event.dart';
part 'crud_state.dart';
@ -69,6 +76,7 @@ class CrudBloc extends Bloc<CrudEvent, CrudState> {
});
on<FetchTodos>((event, emit) async {
emit(PropertyOwnerInfoLoading());
propertyOwner = await SQLServices.instance.readAllBldgOwner();
emit(PropertyInfoLoaded(propertyInfos: propertyOwner));
});
@ -80,269 +88,417 @@ class CrudBloc extends Bloc<CrudEvent, CrudState> {
on<DeleteTodo>((event, emit) async {
await SQLServices.instance.deleteBldgOwner(id: event.id);
add(const FetchTodos());
});
on<UploadBuildingFaas>(((event, emit) async {
emit(UploadBuildingFaasLoading());
List<PropertyInfo> propertyOwner =
await SQLServices.instance.readAllBldgOwner();
for (PropertyInfo infos in propertyOwner) {
//General Description
List<Map<String, dynamic>> genDesc =
await SQLServices.instance.getGeneralDescription(infos.id);
List<GeneralDesc> genDescList =
genDesc.map((map) => GeneralDesc.fromJson2(map)).toList();
GeneralDesc firstGenDesc = genDescList.first;
//Location
List<Map<String, dynamic>> loc =
await SQLServices.instance.getLandRef(infos.id);
List<BldgLoc> locList =
loc.map((map) => BldgLoc.fromJson2(map)).toList();
BldgLoc firstLoc = locList.first;
//Land Refeernce
List<Map<String, dynamic>> landRef =
await SQLServices.instance.getLocation(infos.id);
List<LandRef> landRefList =
landRef.map((map) => LandRef.fromJson2(map)).toList();
LandRef firstLandRef = landRefList.first;
//Assessment
List<Map<String, dynamic>> assessment =
await SQLServices.instance.getBldgAssessment(infos.id);
List<PropertyAssessment> assessList =
assessment.map((map) => PropertyAssessment.fromJson2(map)).toList();
PropertyAssessment firstAssess = assessList.first;
//Structural Materials
List<Map<String, dynamic>> strucMat =
await SQLServices.instance.getStructuralMaterials(infos.id);
List<StructureMaterials> strcuMatList =
strucMat.map((map) => StructureMaterials.fromJson2(map)).toList();
StructureMaterials firstStructMat = strcuMatList.first;
//Additional Items
List<Map<String, dynamic>> addItems =
await SQLServices.instance.getAdditionalItems(infos.id);
List<AdditionalItems> addItemsList =
addItems.map((map) => AdditionalItems.fromJson(map)).toList();
//BLDG Structure
List<Map<String, dynamic>> bldgStructure =
await SQLServices.instance.getBuildingAndStructure(infos.id);
List<BldgAndStructure> bldgStructureList =
bldgStructure.map((map) => BldgAndStructure.fromJson(map)).toList();
DateTime dateIssued = DateTime.parse(firstGenDesc.dateIssued!);
final details = {
"assessed_by_id": event.offlineProfile.id.toString(),
"assessed_by_name": event.offlineProfile.firstName,
"date_created": "{{currentTimestamp}}",
"date_modified": "{{currentTimestamp}}",
"trans_code": infos.transCode,
"tdn": infos.tdn,
"pin": infos.pin,
"fname": infos.fname,
"mname": infos.mname,
"lname": infos.lname,
"bday": infos.bday,
"address": infos.address,
"telno": infos.telno,
"tin": infos.tin,
"admin_user": infos.adminUser,
"admin_address": infos.adminAddress,
"admin_telno": infos.adminTelno,
"admin_tin": infos.adminTin,
"faas_type": infos.faasType,
"gen_code": "5TH",
"bldgappr_location.date_created": "{{currentTimestamp}}",
"bldgappr_location.date_modified": "{{currentTimestamp}}",
"bldgappr_location.street": firstLoc.street,
"bldgappr_location.barangay": firstLoc.barangay,
"bldgappr_location.municipality": firstLoc.municipality,
"bldgappr_location.province": firstLoc.province,
"bldgappr_location.gen_code": "5TH",
"bldgappr_landref.date_created": "{{currentTimestamp}}",
"bldgappr_landref.date_modified": "{{currentTimestamp}}",
"bldgappr_landref.owner": firstLandRef.owner,
"bldgappr_landref.cloa_no": firstLandRef.cloaNo,
"bldgappr_landref.lot_no": firstLandRef.lotNo,
"bldgappr_landref.tdn": firstLandRef.tdn,
"bldgappr_landref.area": firstLandRef.area,
"bldgappr_landref.survey_no": firstLandRef.surveyNo,
"bldgappr_landref.blk_no": firstLandRef.blkNo,
"bldgappr_landref.gen_code": "5TH",
"bldgappr_generaldesc.date_created": "{{currentTimestamp}}",
"bldgappr_generaldesc.date_modified": "{{currentTimestamp}}",
"bldgappr_generaldesc.bldg_kind": firstGenDesc.bldgKind,
"bldgappr_generaldesc.struc_type": firstGenDesc.strucType,
"bldgappr_generaldesc.bldg_permit": firstGenDesc.bldgPermit,
"bldgappr_generaldesc.date_issued": DateFormat("yyyy-MM-dd")
.format(DateTime.parse(firstGenDesc.dateIssued!)),
"bldgappr_generaldesc.cct": null,
"bldgappr_generaldesc.cert_completion_issued":
DateFormat("yyyy-MM-dd")
.format(DateTime.parse(firstGenDesc.certCompletionIssued!)),
"bldgappr_generaldesc.cert_ocscupancy_issued":
DateFormat("yyyy-MM-dd")
.format(DateTime.parse(firstGenDesc.certOccupancyIssued!)),
"bldgappr_generaldesc.date_completed": DateFormat("yyyy-MM-dd")
.format(DateTime.parse(firstGenDesc.dateCompleted!)),
"bldgappr_generaldesc.date_occupied": DateFormat("yyyy-MM-dd")
.format(DateTime.parse(firstGenDesc.dateOccupied!)),
"bldgappr_generaldesc.bldg_age": firstGenDesc.bldgAge,
"bldgappr_generaldesc.no_storeys": firstGenDesc.noStoreys,
"bldgappr_generaldesc.area_1stfloor": firstGenDesc.area1Stfloor,
"bldgappr_generaldesc.area_2ndfloor": firstGenDesc.area2Ndfloor,
"bldgappr_generaldesc.area_3rdfloor": firstGenDesc.area3Rdfloor,
"bldgappr_generaldesc.area_4thfloor": firstGenDesc.area4Thfloor,
"bldgappr_generaldesc.total_floor_area": firstGenDesc.totalFloorArea,
"bldgappr_generaldesc.floor_sketch": null,
"bldgappr_generaldesc.actual_use": firstGenDesc.actualUse,
"bldgappr_generaldesc.unit_value": firstGenDesc.unitValue,
"bldgappr_generaldesc.gen_code": "5TH",
"bldgappr_struct_materials.date_created": "{{currentTimestamp}}",
"bldgappr_struct_materials.date_modified": "{{currentTimestamp}}",
"bldgappr_struct_materials.foundation": firstStructMat.foundation,
"bldgappr_struct_materials.columns": firstStructMat.columns,
"bldgappr_struct_materials.beams": firstStructMat.beams,
"bldgappr_struct_materials.truss_framing":
firstStructMat.trussFraming,
"bldgappr_struct_materials.roof": firstStructMat.roof,
"bldgappr_struct_materials.flooring": firstStructMat.flooring,
"bldgappr_struct_materials.walls": firstStructMat.walls,
"bldgappr_struct_materials.others": firstStructMat.others,
"bldgappr_struct_materials.gen_code": "5TH",
"bldgappr_property_assessment.date_created": "{{currentTimestamp}}",
"bldgappr_property_assessment.date_modified": "{{currentTimestamp}}",
"bldgappr_property_assessment.actual_use": firstAssess.actualUse,
"bldgappr_property_assessment.market_value": firstAssess.marketValue,
"bldgappr_property_assessment.assessment_level":
firstAssess.assessmentLevel,
"bldgappr_property_assessment.assessed_value":
firstAssess.assessedValue,
"bldgappr_property_assessment.taxable": firstAssess.taxable,
"bldgappr_property_assessment.exempt": firstAssess.exempt,
"bldgappr_property_assessment.qtr": firstAssess.qtr,
"bldgappr_property_assessment.yr": firstAssess.yr,
"bldgappr_property_assessment.appraisedby_name":
firstAssess.appraisedbyName,
"bldgappr_property_assessment.appraisedby_date":
DateFormat("yyyy-MM-dd")
.format(DateTime.parse(firstAssess.appraisedbyDate!)),
"bldgappr_property_assessment.recommendappr_name":
firstAssess.recommendapprName,
"bldgappr_property_assessment.recommendappr_date":
DateFormat("yyyy-MM-dd")
.format(DateTime.parse(firstAssess.recommendapprDate!)),
"bldgappr_property_assessment.approvedby_name":
firstAssess.approvedbyName,
"bldgappr_property_assessment.approvedby_date": null,
"bldgappr_property_assessment.memoranda": firstAssess.memoranda,
"bldgappr_property_assessment.swornstatement_no":
firstAssess.swornstatementNo,
"bldgappr_property_assessment.date_received": DateFormat("yyyy-MM-dd")
.format(DateTime.parse(firstAssess.dateReceived!)),
"bldgappr_property_assessment.entry_date_assessment": null,
"bldgappr_property_assessment.entry_date_by": DateFormat("yyyy-MM-dd")
.format(DateTime.parse(firstAssess.entryDateAssessment!)),
"bldgappr_property_assessment.gen_code": "5TH",
"bldgappr_rec_supersededass.date_created": "{{currentTimestamp}}",
"bldgappr_rec_supersededass.date_modified": "{{currentTimestamp}}",
"bldgappr_rec_supersededass.pin": null,
"bldgappr_rec_supersededass.tdn": null,
"bldgappr_rec_supersededass.total_assval": null,
"bldgappr_rec_supersededass.owner": null,
"bldgappr_rec_supersededass.effectivity_ass": null,
"bldgappr_rec_supersededass.page_no": null,
"bldgappr_rec_supersededass.total_marketval": null,
"bldgappr_rec_supersededass.total_area": null,
"bldgappr_rec_supersededass.rec_assessment": null,
"bldgappr_rec_supersededass.rec_taxmapping": null,
"bldgappr_rec_supersededass.rec_records": null,
"bldgappr_rec_supersededass.date": null,
"bldgappr_rec_supersededass.gen_code": "5TH"
};
// print(details);
String xClientKey = "unitK3CQaXiWlPReDsBzmmwBZPd9Re1z";
String xClientKeySecret = "unitcYqAN7GGalyz";
Map<String, String> headers = {
'Content-Type': 'application/json; charset=UTF-8',
'X-Client-Key': xClientKey,
'X-Client-Secret': xClientKeySecret
};
Response details_response = await post(
Uri.parse(
'http://${Url.instance.host()}/api/rptass_app/bldgappr_details/'),
headers: headers,
body: jsonEncode(details));
final datas = json.decode(details_response.body);
for (AdditionalItems items in addItemsList) {
final addItems = AdditionalItems(
id: 1,
bldgapprDetailsId: datas['data']['id'],
classId: items.classId,
className: items.className,
structType: items.structType,
unitValue: items.unitValue,
baseUnitValue: items.baseUnitValue,
area: items.area,
marketValue: items.marketValue,
depreciationRate: items.depreciationRate,
adjustedMarketVal: items.adjustedMarketVal,
amtDepreciation: items.amtDepreciation,
painted: items.painted,
secondhand: items.secondhand,
paintedUnitval: items.paintedUnitval,
secondhandUnitval: items.secondhandUnitval,
actualUse: items.actualUse,
genCode: "5TH");
Response add_response = await post(
Uri.parse(
'http://${Url.instance.host()}/api/rptass_app/additional_items/'),
headers: headers,
body: jsonEncode(addItems));
}
for (BldgAndStructure structure in bldgStructureList) {
final bldgStruc = BldgAndStructure(
id: 1,
bldgapprDetailsId: datas['data']['id'],
bldgArea: structure.bldgArea,
bldgType: structure.bldgType,
structType: structure.structType,
description: structure.description,
actualUse: structure.actualUse,
floorCount: structure.floorCount,
unitValue: structure.unitValue,
depRate: structure.depRate,
marketValue: structure.marketValue,
depAmount: structure.depAmount,
adjustedMarketValue: structure.adjustedMarketValue,
genCode: '5TH',
buccPercentage: structure.buccPercentage);
print(bldgStruc.toJson());
Response response = await post(
Uri.parse(
'http://${Url.instance.host()}/api/rptass_app/bldgappr_structure/'),
headers: headers,
body: jsonEncode(bldgStruc));
}
// Directly fetch and emit new data rather than triggering another event
try {
emit(PropertyOwnerInfoLoading());
propertyOwner.clear(); // Clear the current list
propertyOwner =
await SQLServices.instance.readAllBldgOwner(); // Refetch data
emit(PropertyInfoLoaded(
propertyInfos: propertyOwner)); // Emit new state with updated data
} catch (error) {
// emit((error.toString())); // Handle potential errors
print(error.toString());
}
emit(PropertyInfoLoaded(propertyInfos: propertyOwner));
}));
});
Future<Map<String, dynamic>> _prepareBuildingDetails(
UploadBuildingFaas event, PropertyInfo infos) async {
// Fetch data
List<Map<String, dynamic>> genDesc =
await SQLServices.instance.getGeneralDescription(infos.id);
List<Map<String, dynamic>> loc =
await SQLServices.instance.getLocation(infos.id);
List<Map<String, dynamic>> landRef =
await SQLServices.instance.getLandRef(infos.id);
List<Map<String, dynamic>> assessment =
await SQLServices.instance.getBldgAssessment(infos.id);
List<Map<String, dynamic>> strucMat =
await SQLServices.instance.getStructuralMaterials(infos.id);
List<Map<String, dynamic>> addItems =
await SQLServices.instance.getAdditionalItems(infos.id);
List<Map<String, dynamic>> bldgStructure =
await SQLServices.instance.getBuildingAndStructure(infos.id);
// Parse data
GeneralDesc firstGenDesc = GeneralDesc.fromJson2(genDesc.first);
BldgLoc firstLoc = BldgLoc.fromJson2(loc.first);
LandRef firstLandRef = LandRef.fromJson2(landRef.first);
PropertyAssessment firstAssess =
PropertyAssessment.fromJson2(assessment.first);
StructureMaterials firstStructMat =
StructureMaterials.fromJson2(strucMat.first);
// Prepare details
DateTime dateIssued = DateTime.parse(firstGenDesc.dateIssued!);
final details = {
"assessed_by_id": event.offlineProfile.id.toString(),
"assessed_by_name": event.offlineProfile.firstName,
"date_created": "{{currentTimestamp}}",
"date_modified": "{{currentTimestamp}}",
"trans_code": '08887',
"tdn": infos.tdn,
"pin": infos.pin,
"fname": infos.fname,
"mname": infos.mname,
"lname": infos.lname,
"bday": infos.bday,
"address": infos.address,
"telno": infos.telno,
"tin": infos.tin,
"admin_user": infos.adminUser,
"admin_address": infos.adminAddress,
"admin_telno": infos.adminTelno,
"admin_tin": infos.adminTin,
"faas_type": infos.faasType,
"gen_code": "5TH",
"bldgappr_location.date_created": "{{currentTimestamp}}",
"bldgappr_location.date_modified": "{{currentTimestamp}}",
"bldgappr_location.street": firstLoc.street,
"bldgappr_location.barangay": firstLoc.barangay,
"bldgappr_location.municipality": firstLoc.municipality,
"bldgappr_location.province": firstLoc.province,
"bldgappr_location.gen_code": "5TH",
"bldgappr_landref.date_created": "{{currentTimestamp}}",
"bldgappr_landref.date_modified": "{{currentTimestamp}}",
"bldgappr_landref.owner": firstLandRef.owner,
"bldgappr_landref.cloa_no": firstLandRef.cloaNo,
"bldgappr_landref.lot_no": firstLandRef.lotNo,
"bldgappr_landref.tdn": firstLandRef.tdn,
"bldgappr_landref.area": firstLandRef.area,
"bldgappr_landref.survey_no": firstLandRef.surveyNo,
"bldgappr_landref.blk_no": firstLandRef.blkNo,
"bldgappr_landref.gen_code": "5TH",
"bldgappr_generaldesc.date_created": "{{currentTimestamp}}",
"bldgappr_generaldesc.date_modified": "{{currentTimestamp}}",
"bldgappr_generaldesc.bldg_kind": firstGenDesc.bldgKind,
"bldgappr_generaldesc.struc_type": firstGenDesc.strucType,
"bldgappr_generaldesc.bldg_permit": firstGenDesc.bldgPermit,
"bldgappr_generaldesc.date_issued": DateFormat("yyyy-MM-dd")
.format(DateTime.parse(firstGenDesc.dateIssued!)),
"bldgappr_generaldesc.cct": null,
"bldgappr_generaldesc.cert_completion_issued": DateFormat("yyyy-MM-dd")
.format(DateTime.parse(firstGenDesc.certCompletionIssued!)),
"bldgappr_generaldesc.cert_occupancy_issued": DateFormat("yyyy-MM-dd")
.format(DateTime.parse(firstGenDesc.certOccupancyIssued!)),
"bldgappr_generaldesc.date_completed": DateFormat("yyyy-MM-dd")
.format(DateTime.parse(firstGenDesc.dateCompleted!)),
"bldgappr_generaldesc.date_occupied": DateFormat("yyyy-MM-dd")
.format(DateTime.parse(firstGenDesc.dateOccupied!)),
"bldgappr_generaldesc.bldg_age": firstGenDesc.bldgAge,
"bldgappr_generaldesc.no_storeys": firstGenDesc.noStoreys,
"bldgappr_generaldesc.area_1stfloor": firstGenDesc.area1Stfloor,
"bldgappr_generaldesc.area_2ndfloor": firstGenDesc.area2Ndfloor,
"bldgappr_generaldesc.area_3rdfloor": firstGenDesc.area3Rdfloor,
"bldgappr_generaldesc.area_4thfloor": firstGenDesc.area4Thfloor,
"bldgappr_generaldesc.total_floor_area": firstGenDesc.totalFloorArea,
"bldgappr_generaldesc.floor_sketch": null,
"bldgappr_generaldesc.actual_use": firstGenDesc.actualUse,
"bldgappr_generaldesc.unit_value": firstGenDesc.unitValue,
"bldgappr_generaldesc.gen_code": "5TH",
"bldgappr_struct_materials.date_created": "{{currentTimestamp}}",
"bldgappr_struct_materials.date_modified": "{{currentTimestamp}}",
"bldgappr_struct_materials.foundation": firstStructMat.foundation,
"bldgappr_struct_materials.columns": firstStructMat.columns,
"bldgappr_struct_materials.beams": firstStructMat.beams,
"bldgappr_struct_materials.truss_framing": firstStructMat.trussFraming,
"bldgappr_struct_materials.roof": firstStructMat.roof,
"bldgappr_struct_materials.flooring": firstStructMat.flooring,
"bldgappr_struct_materials.walls": firstStructMat.walls,
"bldgappr_struct_materials.others": firstStructMat.others,
"bldgappr_struct_materials.gen_code": "5TH",
"bldgappr_property_assessment.date_created": "{{currentTimestamp}}",
"bldgappr_property_assessment.date_modified": "{{currentTimestamp}}",
"bldgappr_property_assessment.actual_use": firstAssess.actualUse,
"bldgappr_property_assessment.market_value": firstAssess.marketValue,
"bldgappr_property_assessment.assessment_level":
firstAssess.assessmentLevel,
"bldgappr_property_assessment.assessed_value":
firstAssess.assessedValue,
"bldgappr_property_assessment.taxable": firstAssess.taxable,
"bldgappr_property_assessment.exempt": firstAssess.exempt,
"bldgappr_property_assessment.qtr": firstAssess.qtr,
"bldgappr_property_assessment.yr": firstAssess.yr,
"bldgappr_property_assessment.appraisedby_name":
firstAssess.appraisedbyName,
"bldgappr_property_assessment.appraisedby_designation":
firstAssess.appraisedbyDesignation,
"bldgappr_property_assessment.appraisedby_date":
DateFormat("yyyy-MM-dd")
.format(DateTime.parse(firstAssess.appraisedbyDate!)),
"bldgappr_property_assessment.recommendappr_name":
firstAssess.recommendapprName,
"bldgappr_property_assessment.recommendappr_designation":
firstAssess.recommendapprDesignation,
"bldgappr_property_assessment.recommendappr_date":
DateFormat("yyyy-MM-dd")
.format(DateTime.parse(firstAssess.recommendapprDate!)),
"bldgappr_property_assessment.approvedby_name":
firstAssess.approvedbyName,
"bldgappr_property_assessment.approvedby_designation":
firstAssess.approvedbyDesignation,
"bldgappr_property_assessment.approvedby_date": DateFormat("yyyy-MM-dd")
.format(DateTime.parse(firstAssess.approvedbyDate!)),
"bldgappr_property_assessment.memoranda": firstAssess.memoranda,
"bldgappr_property_assessment.note": firstAssess.note,
"bldgappr_property_assessment.swornstatement_no":
firstAssess.swornstatementNo,
"bldgappr_property_assessment.date_received": DateFormat("yyyy-MM-dd")
.format(DateTime.parse(firstAssess.dateReceived!)),
"bldgappr_property_assessment.entry_date_assessment":
DateFormat("yyyy-MM-dd")
.format(DateTime.parse(firstAssess.entryDateAssessment!)),
"bldgappr_property_assessment.entry_date_by": " ",
"bldgappr_property_assessment.gen_code": "5TH",
"bldgappr_rec_supersededass.date_created": "{{currentTimestamp}}",
"bldgappr_rec_supersededass.date_modified": "{{currentTimestamp}}",
"bldgappr_rec_supersededass.pin": " ",
"bldgappr_rec_supersededass.tdn": " ",
"bldgappr_rec_supersededass.total_assval": "0",
"bldgappr_rec_supersededass.owner": " ",
"bldgappr_rec_supersededass.effectivity_ass": null,
"bldgappr_rec_supersededass.page_no": "0",
"bldgappr_rec_supersededass.total_marketval": "0",
"bldgappr_rec_supersededass.total_area": "0",
"bldgappr_rec_supersededass.rec_assessment": null,
"bldgappr_rec_supersededass.rec_taxmapping": " ",
"bldgappr_rec_supersededass.rec_records": " ",
"bldgappr_rec_supersededass.date": null,
"bldgappr_rec_supersededass.gen_code": "5TH"
};
return details;
}
Future<void> _postAdditionalItems(
Map<String, dynamic> datas, PropertyInfo infos) async {
String xClientKey = "unitK3CQaXiWlPReDsBzmmwBZPd9Re1z";
String xClientKeySecret = "unitcYqAN7GGalyz";
Map<String, String> headers = {
'Content-Type': 'application/json; charset=UTF-8',
'X-Client-Key': xClientKey,
'X-Client-Secret': xClientKeySecret
};
List<Map<String, dynamic>> addItems =
await SQLServices.instance.getAdditionalItems(infos.id);
List<AdditionalItems> addItemsList =
addItems.map((map) => AdditionalItems.fromJson(map)).toList();
for (AdditionalItems items in addItemsList) {
// Populate AdditionalItems model here
final addItems = AdditionalItems(
id: 1,
bldgapprDetailsId: datas['data']['id'],
classId: items.classId,
className: items.className,
structType: items.structType,
unitValue: items.unitValue,
baseUnitValue: items.baseUnitValue,
area: items.area,
marketValue: items.marketValue,
depreciationRate: items.depreciationRate,
adjustedMarketVal: items.adjustedMarketVal,
amtDepreciation: items.amtDepreciation,
painted: items.painted,
secondhand: items.secondhand,
paintedUnitval: items.paintedUnitval,
secondhandUnitval: items.secondhandUnitval,
actualUse: items.actualUse,
genCode: "5TH");
Response addResponse = await post(
Uri.parse(
'http://${Url.instance.host()}/api/rptass_app/additional_items/'),
headers: headers,
body: jsonEncode(addItems));
print(addResponse.body);
}
}
Future<void> _postBuildingStructures(
Map<String, dynamic> datas, PropertyInfo infos) async {
String xClientKey = "unitK3CQaXiWlPReDsBzmmwBZPd9Re1z";
String xClientKeySecret = "unitcYqAN7GGalyz";
Map<String, String> headers = {
'Content-Type': 'application/json; charset=UTF-8',
'X-Client-Key': xClientKey,
'X-Client-Secret': xClientKeySecret
};
List<Map<String, dynamic>> bldgStructures =
await SQLServices.instance.getBuildingAndStructure(infos.id);
List<BldgAndStructure> bldgStructureList =
bldgStructures.map((map) => BldgAndStructure.fromJson(map)).toList();
for (BldgAndStructure structure in bldgStructureList) {
final bldgStruc = BldgAndStructure(
id: 1,
bldgapprDetailsId: datas['data']['id'],
bldgArea: structure.bldgArea,
bldgType: structure.bldgType,
structType: structure.structType,
description: structure.description,
actualUse: structure.actualUse,
floorCount: structure.floorCount,
unitValue: structure.unitValue,
depRate: structure.depRate,
marketValue: structure.marketValue,
depAmount: structure.depAmount,
adjustedMarketValue: structure.adjustedMarketValue,
genCode: '5TH',
buccPercentage: structure.buccPercentage);
Response response = await post(
Uri.parse(
'http://${Url.instance.host()}/api/rptass_app/bldgappr_structure/'),
headers: headers,
body: jsonEncode(bldgStruc));
print(response.body);
}
}
Future<Response> _postBuildingDetails(Map<String, dynamic> details) async {
String xClientKey = "unitK3CQaXiWlPReDsBzmmwBZPd9Re1z";
String xClientKeySecret = "unitcYqAN7GGalyz";
Map<String, String> headers = {
'Content-Type': 'application/json; charset=UTF-8',
'X-Client-Key': xClientKey,
'X-Client-Secret': xClientKeySecret
};
return await post(
Uri.parse(
'http://${Url.instance.host()}/api/rptass_app/bldgappr_details/'),
headers: headers,
body: jsonEncode(details));
}
Future<Response> _postFloorSketch(
Map<String, dynamic> details, file) async {
String xClientKey = "unitK3CQaXiWlPReDsBzmmwBZPd9Re1z";
String xClientKeySecret = "unitcYqAN7GGalyz";
// Construct the headers for the request
Map<String, String> headers = {
'Content-Type': 'multipart/form-data',
'X-Client-Key': xClientKey,
'X-Client-Secret': xClientKeySecret,
};
// Create a MultipartRequest
var request = MultipartRequest(
'POST',
Uri.parse(
'http://${Url.instance.host()}/api/rptass_app/bldgappr_sketch/'),
);
// Add the headers to the request
request.headers.addAll(headers);
// Add JSON data as a field
// Add individual fields to the request
details.forEach((key, value) {
request.fields[key] = value.toString();
});
// Add the floor sketch image file, if it exists
var fileName = basename(file);
request.files.add(
await MultipartFile.fromPath(
'floor_sketch', // Field name in the API
file,
filename: fileName,
),
);
// Send the request and get the response
var streamedResponse = await request.send();
return await Response.fromStream(streamedResponse);
}
Future<void> _uploadImage(data, infos) async {
// Create a map with the required fields
List<Map<String, dynamic>> floorSketch =
await SQLServices.instance.getFloorSketch(infos.id);
// Parse data
FloorSketch firstFs = FloorSketch.fromJson(floorSketch.first);
var file = File(firstFs.floorSketch!);
Map<String, dynamic> detailsMap = {
"bldgappr_details_id": data['data']['id'], // int8 NOT NULL
"date_created": DateTime.now().toIso8601String(), // timestamptz NULL
"floor_sketch": firstFs.floorSketch!, // text NULL
"gen_code": "5TH", // varchar(20) NOT NULL
};
try {
Response response = await _postFloorSketch(detailsMap, file.path);
print(response.body);
if (response.statusCode == 201) {
print('Upload successful');
} else {
print('Upload failed with status: ${response.statusCode}');
}
} catch (e) {
print('Error: $e');
}
}
on<UploadBuildingFaas>((event, emit) async {
emit(UploadBuildingFaasLoading());
try {
List<PropertyInfo> propertyOwner =
await SQLServices.instance.readAllBldgOwner();
for (PropertyInfo infos in propertyOwner) {
final details = await _prepareBuildingDetails(event, infos);
Response detailsResponse = await _postBuildingDetails(details);
final datas = json.decode(detailsResponse.body);
print(datas);
await _postAdditionalItems(datas, infos);
await _postBuildingStructures(datas, infos);
await _uploadImage(datas, infos);
if (detailsResponse.statusCode == 201) {
final detailsInfo = PropertyInfo(
id: infos.id,
transCode: infos.transCode,
assessedById: infos.assessedById,
assessedByName: infos.assessedByName,
tdn: infos.tdn,
pin: infos.pin,
fname: infos.fname,
mname: infos.mname,
bday: infos.bday,
lname: infos.lname,
address: infos.address,
telno: infos.telno,
tin: infos.tin,
adminUser: infos.adminUser,
adminAddress: infos.adminAddress,
adminTin: infos.adminTin,
adminTelno: infos.adminTelno,
faasType: "Building",
dateSynced:
DateFormat('MM/dd/yyyy hh:mm a').format(DateTime.now()));
await SQLServices.instance.updateBldgOwner(infos.id, detailsInfo);
}
}
propertyOwner = await SQLServices.instance.readAllBldgOwner();
emit(PropertyInfoLoaded(propertyInfos: propertyOwner));
} catch (e) {
print(e.toString());
emit(PropertyOwnerInfoErrorState(errorMessage: e.toString()));
}
;
});
}
}

View File

@ -26,7 +26,7 @@ Future main() async {
SOS = await Hive.openBox<dynamic>('soscontacts');
OFFLINE = await Hive.openBox<dynamic>('offline');
SystemChrome.setPreferredOrientations([DeviceOrientation.portraitUp])
SystemChrome.setPreferredOrientations([DeviceOrientation.landscapeLeft])
.then((_) {
runApp(MyApp());
});

View File

@ -2,7 +2,6 @@
//
// final additionalItems = additionalItemsFromJson(jsonString);
import 'package:meta/meta.dart';
import 'dart:convert';
AdditionalItems additionalItemsFromJson(String str) =>

View File

@ -2,7 +2,6 @@
//
// final classComponents = classComponentsFromJson(jsonString);
import 'package:meta/meta.dart';
import 'dart:convert';
ClassComponentsOffline classComponentsFromJson(String str) =>

View File

@ -2,7 +2,6 @@
//
// final classComponents = classComponentsFromJson(jsonString);
import 'package:meta/meta.dart';
import 'dart:convert';
ClassComponents classComponentsFromJson(String str) =>

View File

@ -0,0 +1,64 @@
// To parse this JSON data, do
//
// final floorSketch = floorSketchFromJson(jsonString);
import 'dart:convert';
FloorSketch floorSketchFromJson(String str) =>
FloorSketch.fromJson(json.decode(str));
String floorSketchToJson(FloorSketch data) => json.encode(data.toJson());
class FloorSketch {
final int? bldgapprDetailsId;
final String? dateCreated;
final String? floorSketch;
final String? genCode;
FloorSketch({
this.bldgapprDetailsId,
this.dateCreated,
this.floorSketch,
this.genCode,
});
FloorSketch copy(
{int? bldgapprDetailsId,
String? dateCreated,
String? floorSketch,
String? genCode}) {
return FloorSketch(
bldgapprDetailsId: bldgapprDetailsId ?? this.bldgapprDetailsId,
dateCreated: dateCreated ?? this.dateCreated,
floorSketch: floorSketch ?? this.floorSketch,
genCode: genCode ?? this.genCode,
);
}
FloorSketch copyWith({
int? bldgapprDetailsId,
String? dateCreated,
String? floorSketch,
String? genCode,
}) =>
FloorSketch(
bldgapprDetailsId: bldgapprDetailsId ?? this.bldgapprDetailsId,
dateCreated: dateCreated ?? this.dateCreated,
floorSketch: floorSketch ?? this.floorSketch,
genCode: genCode ?? this.genCode,
);
factory FloorSketch.fromJson(Map<String, dynamic> json) => FloorSketch(
bldgapprDetailsId: json["bldgappr_details_id"],
dateCreated: json["date_created"],
floorSketch: json["floor_sketch"],
genCode: json["gen_code"],
);
Map<String, dynamic> toJson() => {
"bldgappr_details_id": bldgapprDetailsId,
"date_created": dateCreated,
"floor_sketch": floorSketch,
"gen_code": genCode,
};
}

View File

@ -31,6 +31,7 @@ class PropertyAssessment {
final String recommendapprName;
final String recommendapprDate;
final String approvedbyName;
final String approvedbyDate;
final String memoranda;
final String swornstatementNo;
final String dateReceived;
@ -62,6 +63,7 @@ class PropertyAssessment {
required this.recommendapprName,
required this.recommendapprDate,
required this.approvedbyName,
required this.approvedbyDate,
required this.memoranda,
required this.swornstatementNo,
required this.dateReceived,
@ -95,6 +97,7 @@ class PropertyAssessment {
String? recommendapprName,
String? recommendapprDate,
String? approvedbyName,
String? approvedbyDate,
String? memoranda,
String? swornstatementNo,
String? dateReceived,
@ -126,6 +129,7 @@ class PropertyAssessment {
recommendapprName: recommendapprName ?? this.recommendapprName,
recommendapprDate: recommendapprDate ?? this.recommendapprDate,
approvedbyName: approvedbyName ?? this.approvedbyName,
approvedbyDate: approvedbyDate ?? this.approvedbyDate,
memoranda: memoranda ?? this.memoranda,
swornstatementNo: swornstatementNo ?? this.swornstatementNo,
dateReceived: dateReceived ?? this.dateReceived,
@ -162,6 +166,7 @@ class PropertyAssessment {
recommendapprName: json["recommendappr_name"],
recommendapprDate: json["recommendappr_date"],
approvedbyName: json["approvedby_name"],
approvedbyDate: json["approvedby_date"],
memoranda: json["memoranda"],
swornstatementNo: json["swornstatement_no"],
dateReceived: json["date_received"],
@ -195,6 +200,7 @@ class PropertyAssessment {
recommendapprName: json["recommendapprName"],
recommendapprDate: json["recommendapprDate"],
approvedbyName: json["approvedbyName"],
approvedbyDate: json["approvedbyDate"],
memoranda: json["memoranda"],
swornstatementNo: json["swornstatementNo"],
dateReceived: json["dateReceived"],
@ -227,6 +233,7 @@ class PropertyAssessment {
"recommendappr_name": recommendapprName,
"recommendappr_date": recommendapprDate,
"approvedby_name": approvedbyName,
"approvedby_date": approvedbyDate,
"memoranda": memoranda,
"swornstatement_no": swornstatementNo,
"date_received": dateReceived,

View File

@ -31,131 +31,131 @@ class PropertyInfo {
final String? adminTin;
final String? faasType;
final String? genCode;
final String? dateSynced;
PropertyInfo({
this.id,
this.assessedById,
this.assessedByName,
this.dateCreated,
this.dateModified,
this.transCode,
this.tdn,
this.pin,
this.fname,
this.mname,
this.lname,
this.bday,
this.address,
this.telno,
this.tin,
this.adminUser,
this.adminAddress,
this.adminTelno,
this.adminTin,
this.faasType,
this.genCode,
});
PropertyInfo(
{this.id,
this.assessedById,
this.assessedByName,
this.dateCreated,
this.dateModified,
this.transCode,
this.tdn,
this.pin,
this.fname,
this.mname,
this.lname,
this.bday,
this.address,
this.telno,
this.tin,
this.adminUser,
this.adminAddress,
this.adminTelno,
this.adminTin,
this.faasType,
this.genCode,
this.dateSynced});
PropertyInfo copy({
int? id,
String? assessedById,
String? assessedByName,
String? dateCreated,
String? dateModified,
String? transCode,
String? tdn,
String? pin,
String? owner,
String? address,
String? telno,
String? tin,
String? adminUser,
String? adminAddress,
String? adminTelno,
String? adminTin,
String? faasType,
String? genCode,
}) =>
PropertyInfo copy(
{int? id,
String? assessedById,
String? assessedByName,
String? dateCreated,
String? dateModified,
String? transCode,
String? tdn,
String? pin,
String? owner,
String? address,
String? telno,
String? tin,
String? adminUser,
String? adminAddress,
String? adminTelno,
String? adminTin,
String? faasType,
String? genCode,
String? dateSynced}) =>
PropertyInfo(
id: id ?? this.id,
assessedById: assessedById ?? this.assessedById,
assessedByName: assessedByName ?? this.assessedByName,
dateCreated: dateCreated ?? this.dateCreated,
dateModified: dateModified ?? this.dateModified,
transCode: transCode ?? this.transCode,
tdn: tdn ?? this.tdn,
pin: pin ?? this.pin,
fname: fname ?? this.fname,
mname: mname ?? this.mname,
lname: lname ?? this.lname,
bday: bday ?? this.bday,
address: address ?? this.address,
telno: telno ?? this.telno,
tin: tin ?? this.tin,
adminUser: adminUser ?? this.adminUser,
adminAddress: adminAddress ?? this.adminAddress,
adminTelno: adminTelno ?? this.adminTelno,
adminTin: adminTin ?? this.adminTin,
faasType: faasType ?? this.faasType,
genCode: genCode ?? this.genCode,
);
id: id ?? this.id,
assessedById: assessedById ?? this.assessedById,
assessedByName: assessedByName ?? this.assessedByName,
dateCreated: dateCreated ?? this.dateCreated,
dateModified: dateModified ?? this.dateModified,
transCode: transCode ?? this.transCode,
tdn: tdn ?? this.tdn,
pin: pin ?? this.pin,
fname: fname ?? this.fname,
mname: mname ?? this.mname,
lname: lname ?? this.lname,
bday: bday ?? this.bday,
address: address ?? this.address,
telno: telno ?? this.telno,
tin: tin ?? this.tin,
adminUser: adminUser ?? this.adminUser,
adminAddress: adminAddress ?? this.adminAddress,
adminTelno: adminTelno ?? this.adminTelno,
adminTin: adminTin ?? this.adminTin,
faasType: faasType ?? this.faasType,
genCode: genCode ?? this.genCode,
dateSynced: dateSynced ?? this.dateSynced);
factory PropertyInfo.fromJson(Map<String, dynamic> json) => PropertyInfo(
id: json["id"],
assessedById: json["assessed_by_id"],
assessedByName: json["assessed_by_name"],
// dateCreated: json["date_created"] == null
// ? null
// : DateTime.parse(json["date_created"]),
// dateModified: json["date_modified"] == null
// ? null
// : DateTime.parse(json["date_modified"]),
transCode: json["trans_code"],
tdn: json["tdn"],
pin: json["pin"],
fname: json["fname"],
mname: json["mname"],
lname: json["lname"],
bday: json["bday"],
address: json["address"],
telno: json["telno"],
tin: json["tin"],
adminUser: json["admin_user"],
adminAddress: json["admin_address"],
adminTelno: json["admin_telno"],
adminTin: json["admin_tin"],
faasType: json["faas_type"],
genCode: json["gen_code"],
);
id: json["id"],
assessedById: json["assessed_by_id"],
assessedByName: json["assessed_by_name"],
// dateCreated: json["date_created"] == null
// ? null
// : DateTime.parse(json["date_created"]),
// dateModified: json["date_modified"] == null
// ? null
// : DateTime.parse(json["date_modified"]),
transCode: json["trans_code"],
tdn: json["tdn"],
pin: json["pin"],
fname: json["fname"],
mname: json["mname"],
lname: json["lname"],
bday: json["bday"],
address: json["address"],
telno: json["telno"],
tin: json["tin"],
adminUser: json["admin_user"],
adminAddress: json["admin_address"],
adminTelno: json["admin_telno"],
adminTin: json["admin_tin"],
faasType: json["faas_type"],
genCode: json["gen_code"],
dateSynced: json["dateSynced"]);
factory PropertyInfo.fromJson2(Map<String, dynamic> json) => PropertyInfo(
id: json["id"],
assessedById: json["assessedById"],
assessedByName: json["assessedByName"],
// dateCreated: json["date_created"] == null
// ? null
// : DateTime.parse(json["date_created"]),
// dateModified: json["date_modified"] == null
// ? null
// : DateTime.parse(json["date_modified"]),
transCode: json["transCode"],
tdn: json["tdn"],
pin: json["pin"],
fname: json["fname"],
mname: json["mname"],
lname: json["lname"],
bday: json["bday"],
address: json["address"],
telno: json["telno"],
tin: json["tin"],
adminUser: json["adminUser"],
adminAddress: json["adminAddress"],
adminTelno: json["adminTelno"],
adminTin: json["adminTin"],
faasType: json["faasType"],
genCode: json["genCode"],
);
id: json["id"],
assessedById: json["assessedById"],
assessedByName: json["assessedByName"],
// dateCreated: json["date_created"] == null
// ? null
// : DateTime.parse(json["date_created"]),
// dateModified: json["date_modified"] == null
// ? null
// : DateTime.parse(json["date_modified"]),
transCode: json["transCode"],
tdn: json["tdn"],
pin: json["pin"],
fname: json["fname"],
mname: json["mname"],
lname: json["lname"],
bday: json["bday"],
address: json["address"],
telno: json["telno"],
tin: json["tin"],
adminUser: json["adminUser"],
adminAddress: json["adminAddress"],
adminTelno: json["adminTelno"],
adminTin: json["adminTin"],
faasType: json["faasType"],
genCode: json["genCode"],
dateSynced: json["dateSynced"]);
factory PropertyInfo.fromMap(Map<String, dynamic> map) => PropertyInfo(
id: map["id"],
@ -178,7 +178,8 @@ class PropertyInfo {
adminTelno: map["adminTelno"],
adminTin: map["adminTin"],
faasType: map["faasType"],
genCode: map["genCode"]);
genCode: map["genCode"],
dateSynced: map["dateSynced"]);
Map<String, dynamic> toJson() => {
"id": id,
@ -202,5 +203,6 @@ class PropertyInfo {
"admin_tin": adminTin,
"faas_type": faasType,
"gen_code": genCode,
"dateSynced": dateSynced
};
}

View File

@ -40,6 +40,13 @@ class UnitConstruct {
);
}
UnitConstruct.defaultConstruct()
: id = 0,
bldgType = 'defaultType',
building = 'defaultBuilding',
unitValue = '0',
genCode = 'defaultGenCode';
factory UnitConstruct.fromJson2(Map<String, dynamic> json) => UnitConstruct(
id: json["id"],
bldgType: json["bldgType"],

View File

@ -3,7 +3,6 @@
// final familyBackground = familyBackgroundFromJson(jsonString);
import 'dart:convert';
import 'dart:ffi';
import '../utils/category.dart';
import '../utils/position.dart';

View File

@ -1,4 +1,3 @@
import 'package:flutter/material.dart';
import 'package:flutter_form_builder/flutter_form_builder.dart';
import 'package:fluttericon/entypo_icons.dart';
@ -38,11 +37,13 @@ class _RequetAutoReceiptState extends State<RequetAutoReceipt> {
Column(crossAxisAlignment: CrossAxisAlignment.start, children: [
const DocInfo(title: "4427", subTitle: documentId),
const CostumDivider(),
const DocInfo(title: "Purchase of Diesel", subTitle: documentTitle),
const DocInfo(
title: "Purchase of Diesel", subTitle: documentTitle),
const CostumDivider(),
const DocInfo(title: "N/A", subTitle: documentSubject),
const CostumDivider(),
const DocInfo(title: "Request for Quotation", subTitle: documentType),
const DocInfo(
title: "Request for Quotation", subTitle: documentType),
const CostumDivider(),
Form(
child: Column(children: [
@ -60,20 +61,20 @@ class _RequetAutoReceiptState extends State<RequetAutoReceipt> {
),
Text(
sourceRemarks,
style: Theme.of(context).textTheme.caption,
style: Theme.of(context).textTheme.bodyMedium,
),
const SizedBox(
height: 12,
),
FormBuilderTextField(
name: "remarks",
validator: FormBuilderValidators.required(
errorText: remarksRequired),
validator: FormBuilderValidators.required(
errorText: remarksRequired),
autovalidateMode:
AutovalidateMode.onUserInteraction,
maxLines: 5,
decoration: normalTextFieldStyle(
enterRemarks, "..."),
decoration:
normalTextFieldStyle(enterRemarks, "..."),
),
const SizedBox(
height: 8,
@ -123,8 +124,8 @@ class _RequetAutoReceiptState extends State<RequetAutoReceipt> {
width: double.infinity,
height: screenHeight * .06,
child: ElevatedButton(
style: secondaryBtnStyle(
primary, Colors.transparent, Colors.white54),
style: secondaryBtnStyle(primary,
Colors.transparent, Colors.white54),
child: const Text(
requestAutoReceipt,
style: TextStyle(color: Colors.white),

View File

@ -54,7 +54,7 @@ class OfflineModuleScreen extends StatelessWidget {
children: state.offlineModules
.map((e) => CardLabel(
icon: FontAwesome5.eye,
title: "Field Surveyor",
title: "Rpass Offline",
ontap: () {
Navigator.push(context,
MaterialPageRoute(builder: ((context) {

View File

@ -46,22 +46,22 @@ class _AdminMainScreen extends State<AdminMainScreen> {
backgroundColor: primary,
title: const Text("PASSO Admin"),
centerTitle: true,
actions: [
TextButton(
style: TextButton.styleFrom(
textStyle: const TextStyle(fontSize: 15),
),
onPressed: () async {
try {
GlobalSyncService().syncAllData();
} catch (e) {
// Handle any errors that might occur during the API call or database insertion.
print("Error: $e");
}
},
child: const Text('SYNC'),
),
],
// actions: [
// TextButton(
// style: TextButton.styleFrom(
// textStyle: const TextStyle(fontSize: 15),
// ),
// onPressed: () async {
// try {
// GlobalSyncService().syncAllData();
// } catch (e) {
// // Handle any errors that might occur during the API call or database insertion.
// print("Error: $e");
// }
// },
// child: const Text('SYNC'),
// ),
// ],
),
body: ListView(
children: [
@ -82,7 +82,7 @@ class _AdminMainScreen extends State<AdminMainScreen> {
const Divider(),
MainMenu(
icon: Elusive.wrench,
title: "Barangays",
title: "Barangay",
onTap: () {
Navigator.push(context,
MaterialPageRoute(builder: (BuildContext context) {

View File

@ -21,7 +21,7 @@ class _BarangayAdminPage extends State<BarangayAdminPage> {
return Scaffold(
appBar: AppBar(
backgroundColor: primary,
title: const Text("Municipaities"),
title: const Text("Barangay"),
centerTitle: true,
actions: [
TextButton(
@ -40,6 +40,8 @@ class _BarangayAdminPage extends State<BarangayAdminPage> {
for (Brgy brgy in brgys) {
await SQLServices.instance.createBarangay(brgy);
}
context.read<BarangayAdminBloc>().add(LoadBarangay());
} catch (e) {
// Handle any errors that might occur during the API call or database insertion.
print("Error: $e");

View File

@ -73,6 +73,10 @@ class _ClassComponentsAdminPage extends State<ClassComponentsAdminPage> {
}
}
context
.read<ClassComponentsAdminBloc>()
.add(LoadClassComponents());
// Assuming result is a List of JSON objects, convert them to City objects.
} catch (e) {
// Handle any errors that might occur during the API call or database insertion.

View File

@ -59,6 +59,8 @@ class _MemorandaAdminPage extends State<MemorandaAdminPage> {
await SQLServices.instance.createMemoranda(memo);
}
}
context.read<MemorandaAdminBloc>().add(LoadMemoranda());
} catch (e) {
// Handle any errors that might occur during the API call or database insertion.
print("Error: $e");

View File

@ -43,6 +43,10 @@ class _MunicipalitiesAdminPage extends State<MunicipalitiesAdminPage> {
print(city.cityCode);
await SQLServices.instance.createMunicipalities(city);
}
context
.read<MunicipalitiesAdminBloc>()
.add(LoadMunicipalities());
} catch (e) {
// Handle any errors that might occur during the API call or database insertion.
print("Error: $e");

View File

@ -54,6 +54,7 @@ class _SignatoriesAdminPage extends State<SignatoriesAdminPage> {
await SQLServices.instance.createSignatories(signatory);
}
}
context.read<SignatoriesAdminBloc>().add(LoadSignatories());
} catch (e) {
// Handle any errors that might occur during the API call or database insertion.
print("Error: $e");

View File

@ -13,6 +13,8 @@ import '../../../../sevices/offline/offline_passo/admin/sql_services/sql_service
import '../../../../theme-data.dart/colors.dart';
import 'package:http/http.dart';
import '../../../../utils/urls.dart';
class UnitConstructionAdminPage extends StatefulWidget {
const UnitConstructionAdminPage();
@ -27,7 +29,7 @@ class _UnitConstructionAdminPage extends State<UnitConstructionAdminPage> {
return Scaffold(
appBar: AppBar(
backgroundColor: primary,
title: const Text("Unit Construction"),
title: const Text("Structural Types"),
centerTitle: true,
actions: [
TextButton(
@ -45,7 +47,7 @@ class _UnitConstructionAdminPage extends State<UnitConstructionAdminPage> {
// Loop through the list of City objects and insert them into the local database.
Response response = await get(Uri.parse(
'http://192.168.80.20:8000/api/rptass_app/unitconstruct_values/'));
'http://${Url.instance.host()}/api/rptass_app/unitconstruct_values/'));
print(response.body);
if (response.statusCode == 200) {
@ -60,6 +62,10 @@ class _UnitConstructionAdminPage extends State<UnitConstructionAdminPage> {
for (UnitConstruct unit in units) {
await SQLServices.instance.createUnitConstruction(unit);
}
context
.read<UnitConstructionAdminBloc>()
.add(LoadUnitConstruct());
}
} catch (e) {
// Handle any errors that might occur during the API call or database insertion.

View File

@ -1,3 +1,5 @@
import 'dart:convert';
import 'package:flutter/material.dart';
import 'package:flutter_bloc/flutter_bloc.dart';
import 'package:flutter_form_builder/flutter_form_builder.dart';
@ -14,6 +16,18 @@ import '../../../../../model/passo/unit_construct.dart';
import '../../../../../theme-data.dart/form-style.dart';
import '../../../../../widgets/passo/custom_formBuilder_fields.dart';
// Function to get stored building type
Future<UnitConstruct> getStoredBldgType() async {
SharedPreferences prefs = await SharedPreferences.getInstance();
String? jsonString = prefs.getString('selected_bldg_type');
if (jsonString != null) {
Map<String, dynamic> json = jsonDecode(jsonString);
return UnitConstruct.fromJson(json);
}
// Return a default UnitConstruct if no data is found
return UnitConstruct.defaultConstruct();
}
class AddBuildingAndStructureOffline extends StatefulWidget {
final OfflineProfile offlineProfile;
AddBuildingAndStructureOffline(this.offlineProfile);
@ -33,7 +47,8 @@ class _AddBuildingAndStructureOffline
_AddBuildingAndStructureOffline()
: now = DateTime.now(),
formatter = DateFormat.yMMMMd('en_US').format(DateTime.now());
formatter = DateFormat.yMMMMd('en_US').format(DateTime.now()),
_unitConstruct = UnitConstruct.defaultConstruct();
final actual_use = [
"Residential",
@ -47,6 +62,22 @@ class _AddBuildingAndStructureOffline
String _structureType = "";
double _areaValue = 0;
double _depRate = 0;
UnitConstruct _unitConstruct;
bool _isLoading = true;
@override
void initState() {
super.initState();
_loadData();
}
Future<void> _loadData() async {
UnitConstruct unitConstruct = await getStoredBldgType();
setState(() {
_unitConstruct = unitConstruct;
_isLoading = false;
});
}
double _totalMarketValue(unitBase, bldgArea) {
return unitBase * bldgArea;
@ -62,6 +93,14 @@ class _AddBuildingAndStructureOffline
return marketVal - depAmount;
}
void assignSelectedBldgValues() async {
UnitConstruct? storedBldgType = await getStoredBldgType();
_unitBase = double.parse(storedBldgType!.unitValue);
_structureType = '${storedBldgType.bldgType} - ${storedBldgType.building}';
formKey.currentState!.patchValue({'unit_value': storedBldgType.unitValue});
}
@override
Widget build(BuildContext context) {
return BlocConsumer<BuildingAndStructureBloc, BuildingAndStructureState>(
@ -91,12 +130,34 @@ class _AddBuildingAndStructureOffline
crossAxisAlignment: CrossAxisAlignment.start,
mainAxisSize: MainAxisSize.min,
children: <Widget>[
Container(
margin: const EdgeInsets.only(
left: 0, top: 10, right: 0, bottom: 0),
child: FormBuilderDropdown<String?>(
name: 'actual_use',
autofocus: false,
decoration: normalTextFieldStyle("Actual Use", ""),
items: actual_use
.map((item) => DropdownMenuItem(
value: item,
child: Text(item),
))
.toList(),
onChanged: (value) {
assignSelectedBldgValues();
},
),
),
const SizedBox(
height: 10,
),
Container(
margin: const EdgeInsets.only(
left: 0, top: 10, right: 0, bottom: 0),
child: SizedBox(
height: 45,
child: SearchField(
enabled: false,
itemHeight: 70,
suggestions: state.unit
.map((UnitConstruct unit) =>
@ -115,7 +176,10 @@ class _AddBuildingAndStructureOffline
errorText: "This field is required"),
searchInputDecoration: normalTextFieldStyle(
"Structure Type", "")
_unitConstruct!.bldgType +
' - ' +
_unitConstruct!.building,
"")
.copyWith(
suffixIcon:
const Icon(Icons.arrow_drop_down)),
@ -123,15 +187,7 @@ class _AddBuildingAndStructureOffline
focusNode: focus,
suggestionState: Suggestion.expand,
onSuggestionTap: (unit) {
setState(() {
_unitBase =
double.parse(unit.item!.unitValue);
_structureType =
'${unit.item!.bldgType} - ${unit.item!.building}';
formKey.currentState!.patchValue(
{'unit_value': unit.item?.unitValue});
});
setState(() {});
focus.unfocus();
},
),
@ -140,19 +196,12 @@ class _AddBuildingAndStructureOffline
const SizedBox(
height: 10,
),
customDropDownField(
"Actual Use", "", 'actual_use', actual_use),
const SizedBox(
height: 5,
),
const SizedBox(
height: 10,
),
Container(
child: FormBuilderTextField(
name: 'unit_value',
decoration: normalTextFieldStyle("Unit Value", ""),
validator: FormBuilderValidators.compose([]),
keyboardType: TextInputType.phone,
onChanged: (value) {
// setState(() {
// _areaValue = int.parse(value!);
@ -170,6 +219,7 @@ class _AddBuildingAndStructureOffline
name: 'dep_rate',
decoration: normalTextFieldStyle(
"Depreciation Rate", ""),
keyboardType: TextInputType.phone,
validator: FormBuilderValidators.compose([]),
onChanged: (value) {
setState(() {
@ -186,6 +236,7 @@ class _AddBuildingAndStructureOffline
name: 'bldg_area',
decoration: normalTextFieldStyle("Area", ""),
validator: FormBuilderValidators.compose([]),
keyboardType: TextInputType.phone,
onChanged: (value) {
setState(() {
_areaValue = double.parse(value!);
@ -313,7 +364,7 @@ class _AddBuildingAndStructureOffline
}
},
style: ElevatedButton.styleFrom(
primary: Colors.black,
backgroundColor: Colors.black,
),
child: const Text("Submit"),
),
@ -332,7 +383,7 @@ class _AddBuildingAndStructureOffline
.add(const LoadBuildingAndStructure());
},
style: ElevatedButton.styleFrom(
primary: Colors.black,
backgroundColor: Colors.black,
),
child: const Text("Cancel"),
),
@ -342,7 +393,7 @@ class _AddBuildingAndStructureOffline
],
),
),
);
); // Use your actual widget
}
return Container();
},

View File

@ -1,3 +1,5 @@
import 'dart:convert';
import 'package:flutter/material.dart';
import 'package:flutter_bloc/flutter_bloc.dart';
import 'package:flutter_form_builder/flutter_form_builder.dart';
@ -11,12 +13,25 @@ import 'package:unit2/bloc/offline/offline_passo/admin/unit_construction/unit_co
import 'package:unit2/bloc/offline/offline_passo/building/additional_items_offline/additional_items_offline_bloc.dart';
import 'package:unit2/model/offline/offline_profile.dart';
import 'package:unit2/model/passo/additional_items.dart';
import 'package:unit2/model/passo/class_components%20_offline.dart';
import 'package:unit2/model/passo/class_components.dart';
import 'package:unit2/model/passo/unit_construct.dart';
import 'package:unit2/theme-data.dart/form-style.dart';
import 'package:unit2/utils/text_container.dart';
import 'package:unit2/widgets/error_state.dart';
// Function to get stored building type
Future<UnitConstruct> getStoredBldgType() async {
SharedPreferences prefs = await SharedPreferences.getInstance();
String? jsonString = prefs.getString('selected_bldg_type');
if (jsonString != null) {
Map<String, dynamic> json = jsonDecode(jsonString);
return UnitConstruct.fromJson(json);
}
// Return a default UnitConstruct if no data is found
return UnitConstruct.defaultConstruct();
}
class AddExtraItemsOffline extends StatefulWidget {
final OfflineProfile offlineProfile;
AddExtraItemsOffline(this.offlineProfile);
@ -28,6 +43,7 @@ class AddExtraItemsOffline extends StatefulWidget {
class _AddExtraItemsOffline extends State<AddExtraItemsOffline> {
GlobalKey<FormBuilderState> formKey = GlobalKey<FormBuilderState>();
final focus = FocusNode();
final focusAddItems = FocusNode();
bool isPainted = false;
bool isSecondHand = false;
TextEditingController textEditingController = TextEditingController();
@ -47,7 +63,26 @@ class _AddExtraItemsOffline extends State<AddExtraItemsOffline> {
_AddExtraItemsOffline()
: now = DateTime.now(),
formatter = DateFormat.yMMMMd('en_US').format(DateTime.now());
formatter = DateFormat.yMMMMd('en_US').format(DateTime.now()),
_unitConstruct = UnitConstruct.defaultConstruct();
UnitConstruct _unitConstruct;
bool _isLoading = true;
@override
void initState() {
super.initState();
_loadData();
}
Future<void> _loadData() async {
UnitConstruct unitConstruct = await getStoredBldgType();
setState(() {
_unitConstruct = unitConstruct;
_isLoading = false;
});
}
BoxDecoration box1() {
return const BoxDecoration(boxShadow: [
@ -75,6 +110,30 @@ class _AddExtraItemsOffline extends State<AddExtraItemsOffline> {
}
}
double _calculateMarketValue(unitVal, unitBase, area, withBUCC) {
if (withBUCC == false) {
return ((unitVal * unitBase) * area);
} else {
return (unitVal * area);
}
}
void assignSelectedBldgValues() async {
UnitConstruct? storedBldgType = await getStoredBldgType();
if (_withoutBUCC) {
_unitBase = _unitValue;
_structureType =
storedBldgType!.bldgType + ' - ' + storedBldgType.building;
formKey.currentState!.patchValue({'buccValue': '100'});
} else {
_unitBase = double.parse(storedBldgType!.unitValue);
_structureType =
storedBldgType!.bldgType + ' - ' + storedBldgType.building;
;
formKey.currentState!.patchValue({'unitValue': storedBldgType.unitValue});
}
}
@override
Widget build(BuildContext context) {
return BlocBuilder<AdditionalItemsOfflineBloc, AdditionalItemsOfflineState>(
@ -115,135 +174,208 @@ class _AddExtraItemsOffline extends State<AddExtraItemsOffline> {
left: 0, top: 10, right: 0, bottom: 0),
child: SizedBox(
height: 45,
width: 300,
child: FormBuilderDropdown(
name: 'extra_item',
autofocus: false,
decoration: normalTextFieldStyle(
"Additional Item", ""),
items: classes
.map((e) => DropdownMenuItem(
value: e,
child: Text(e.componentName!),
))
child: SearchField(
itemHeight: 70,
suggestions: classes
.map((ClassComponentsOffline clss) =>
SearchFieldListItem(
'${clss.componentName}',
item: clss,
child: ListTile(
title: Text(
'${clss.componentName}',
overflow:
TextOverflow.ellipsis,
),
)))
.toList(),
onChanged: (value) {
if (value!.minBaseUnitvalPercent !=
'0.00') {
setState(() {
_unitValue = double.parse(
value.minBaseUnitvalPercent!);
_className = value.componentName!;
_classId = value.id!;
_withoutBUCC = value.withoutBucc == 1
? true
: false;
});
formKey.currentState!.patchValue({
'unitValue':
value.minBaseUnitvalPercent
});
}
if (value.maxBaseUnitvalPercent !=
'0.00') {
setState(() {
_unitValue = double.parse(
value.maxBaseUnitvalPercent!);
_className = value.componentName!;
_classId = value.id!;
_withoutBUCC = value.withoutBucc == 1
? true
: false;
});
formKey.currentState!.patchValue({
'unitValue':
value.maxBaseUnitvalPercent
});
}
if (value.minUnitvalSqrmtr != '0.00') {
setState(() {
_unitValue = double.parse(
value.minUnitvalSqrmtr!);
_className = value.componentName!;
_classId = value.id!;
_withoutBUCC = value.withoutBucc == 1
? true
: false;
});
formKey.currentState!.patchValue({
'unitValue': value.minUnitvalSqrmtr
});
}
if (value.maxUnitvalSqrmtr != '0.00') {
setState(() {
_unitValue = double.parse(
value.maxUnitvalSqrmtr!);
_className = value.componentName!;
_classId = value.id!;
_withoutBUCC = value.withoutBucc == 1
? true
: false;
});
formKey.currentState!.patchValue({
'unitValue': value.maxUnitvalSqrmtr
});
}
if (value.minAddBaseunitval != '0.00') {
setState(() {
_unitValue = double.parse(
value.minAddBaseunitval!);
_className = value.componentName!;
_classId = value.id!;
_withoutBUCC = value.withoutBucc == 1
? true
: false;
});
formKey.currentState!.patchValue({
'unitValue': value.minAddBaseunitval
});
}
if (value.maxAddBaseunitval != '0.00') {
setState(() {
_unitValue = double.parse(
value.maxAddBaseunitval!);
_className = value.componentName!;
_classId = value.id!;
_withoutBUCC = value.withoutBucc == 1
? true
: false;
});
formKey.currentState!.patchValue({
'unitValue': value.maxAddBaseunitval
});
}
if (value.minDeductBaserate != '0.00') {
setState(() {
_unitValue = double.parse(
value.minDeductBaserate!);
_className = value.componentName!;
_classId = value.id!;
_withoutBUCC = value.withoutBucc == 1
? true
: false;
});
formKey.currentState!.patchValue({
'unitValue': value.minDeductBaserate
});
}
if (value.maxDeductBaserate != '0.00') {
setState(() {
_unitValue = double.parse(
value.maxDeductBaserate!);
_className = value.componentName!;
_classId = value.id!;
_withoutBUCC = value.withoutBucc == 1
? true
: false;
});
formKey.currentState!.patchValue({
'unitValue': value.maxDeductBaserate
});
}
validator: FormBuilderValidators.required(
errorText: "This field is required"),
searchInputDecoration: normalTextFieldStyle(
"Additional Improvements", "")
.copyWith(
suffixIcon: const Icon(
Icons.arrow_drop_down)),
////agency suggestion tap
focusNode: focusAddItems,
suggestionState: Suggestion.expand,
onSuggestionTap: (value) {
setState(() {
if (value.item!.minBaseUnitvalPercent !=
'0.00') {
setState(() {
_unitValue = double.parse(value
.item!.minBaseUnitvalPercent!);
_className =
value.item!.componentName!;
_classId = value.item!.id!;
_withoutBUCC =
value.item!.withoutBucc == 1
? true
: false;
});
formKey.currentState!.patchValue({
'unitValue': value
.item!.minBaseUnitvalPercent
});
formKey.currentState!.patchValue({
'buccValue': (double.parse(value
.item!
.minBaseUnitvalPercent!) *
100)
.toString()
});
}
if (value.item!.maxBaseUnitvalPercent !=
'0.00') {
setState(() {
_unitValue = double.parse(value
.item!.maxBaseUnitvalPercent!);
_className =
value.item!.componentName!;
_classId = value.item!.id!;
_withoutBUCC =
value.item!.withoutBucc == 1
? true
: false;
});
formKey.currentState!.patchValue({
'unitValue': value
.item!.maxBaseUnitvalPercent
});
formKey.currentState!.patchValue({
'buccValue': (double.parse(value
.item!
.maxBaseUnitvalPercent!) *
100)
.toString()
});
}
if (value.item!.minUnitvalSqrmtr !=
'0.00') {
setState(() {
_unitValue = double.parse(
value.item!.minUnitvalSqrmtr!);
_className =
value.item!.componentName!;
_classId = value.item!.id!;
_withoutBUCC =
value.item!.withoutBucc == 1
? true
: false;
});
formKey.currentState!.patchValue({
'unitValue':
value.item!.minUnitvalSqrmtr
});
formKey.currentState!
.patchValue({'buccValue': '100'});
}
if (value.item!.maxUnitvalSqrmtr !=
'0.00') {
setState(() {
_unitValue = double.parse(
value.item!.maxUnitvalSqrmtr!);
_className =
value.item!.componentName!;
_classId = value.item!.id!;
_withoutBUCC =
value.item!.withoutBucc == 1
? true
: false;
});
formKey.currentState!.patchValue({
'unitValue':
value.item!.maxUnitvalSqrmtr
});
formKey.currentState!
.patchValue({'buccValue': '100'});
}
if (value.item!.minAddBaseunitval !=
'0.00') {
setState(() {
_unitValue = double.parse(
value.item!.minAddBaseunitval!);
_className =
value.item!.componentName!;
_classId = value.item!.id!;
_withoutBUCC =
value.item!.withoutBucc == 1
? true
: false;
});
formKey.currentState!.patchValue({
'unitValue':
value.item!.minAddBaseunitval
});
formKey.currentState!
.patchValue({'buccValue': '100'});
}
if (value.item!.maxAddBaseunitval !=
'0.00') {
setState(() {
_unitValue = double.parse(
value.item!.maxAddBaseunitval!);
_className =
value.item!.componentName!;
_classId = value.item!.id!;
_withoutBUCC =
value.item!.withoutBucc == 1
? true
: false;
});
formKey.currentState!.patchValue({
'unitValue':
value.item!.maxAddBaseunitval
});
formKey.currentState!
.patchValue({'buccValue': '100'});
}
if (value.item!.minDeductBaserate !=
'0.00') {
setState(() {
_unitValue = double.parse(
value.item!.minDeductBaserate!);
_className =
value.item!.componentName!;
_classId = value.item!.id!;
_withoutBUCC =
value.item!.withoutBucc == 1
? true
: false;
});
formKey.currentState!.patchValue({
'unitValue':
value.item!.minDeductBaserate
});
formKey.currentState!
.patchValue({'buccValue': '100'});
}
if (value.item!.maxDeductBaserate !=
'0.00') {
setState(() {
_unitValue = double.parse(
value.item!.maxDeductBaserate!);
_className =
value.item!.componentName!;
_classId = value.item!.id!;
_withoutBUCC =
value.item!.withoutBucc == 1
? true
: false;
});
formKey.currentState!.patchValue({
'unitValue':
value.item!.maxDeductBaserate
});
formKey.currentState!
.patchValue({'buccValue': '100'});
}
assignSelectedBldgValues();
focusAddItems.unfocus();
});
},
),
),
@ -255,15 +387,20 @@ class _AddExtraItemsOffline extends State<AddExtraItemsOffline> {
child: SizedBox(
height: 45,
child: SearchField(
enabled: false,
itemHeight: 70,
suggestions: state.unit
.map((UnitConstruct unit) =>
SearchFieldListItem(
'${unit.bldgType} - ${unit.building}',
_unitConstruct.bldgType +
' - ' +
_unitConstruct.building,
item: unit,
child: ListTile(
title: Text(
'${unit.bldgType} - ${unit.building!.toUpperCase()}',
_unitConstruct.bldgType +
' - ' +
_unitConstruct.building,
overflow:
TextOverflow.ellipsis,
),
@ -274,7 +411,10 @@ class _AddExtraItemsOffline extends State<AddExtraItemsOffline> {
errorText: "This field is required"),
searchInputDecoration: normalTextFieldStyle(
"Structure Type", "")
_unitConstruct.bldgType +
' - ' +
_unitConstruct.building,
"")
.copyWith(
suffixIcon: const Icon(
Icons.arrow_drop_down)),
@ -282,51 +422,12 @@ class _AddExtraItemsOffline extends State<AddExtraItemsOffline> {
focusNode: focus,
suggestionState: Suggestion.expand,
onSuggestionTap: (unit) {
setState(() {
if (_withoutBUCC) {
_unitBase = double.parse(
unit.item!.unitValue);
_structureType =
'${unit.item!.bldgType} - ${unit.item!.building}';
} else {
_unitBase = double.parse(
unit.item!.unitValue);
_structureType =
'${unit.item!.bldgType} - ${unit.item!.building}';
formKey.currentState!.patchValue({
'unitValue': unit.item!.unitValue
});
}
});
setState(() {});
focus.unfocus();
},
),
),
),
// const SizedBox(height: 10),
// Container(
// margin: const EdgeInsets.only(
// left: 0, top: 10, right: 0, bottom: 0),
// child: FormBuilderDropdown(
// name: 'struc_type',
// autofocus: false,
// decoration:
// normalTextFieldStyle("Structure Type", ""),
// items: widget.unit
// .map((e) => DropdownMenuItem(
// value: e,
// child:
// Text(e.bldgType + " - " + e.building),
// ))
// .toList(),
// onChanged: (val) {
// setState(() {
// _unitBase = double.parse(val!.unitValue);
// _structureType = val.bldgType;
// });
// },
// ),
// ),
const SizedBox(height: 10),
Row(
children: [
@ -336,17 +437,54 @@ class _AddExtraItemsOffline extends State<AddExtraItemsOffline> {
name: 'unitValue',
decoration: normalTextFieldStyle(
"Unit Value", ""),
keyboardType: TextInputType.phone,
validator:
FormBuilderValidators.compose([]),
),
),
const SizedBox(width: 10),
Expanded(
flex: 1,
child: FormBuilderTextField(
name: 'buccValue',
decoration:
normalTextFieldStyle("BUCC", ""),
keyboardType: TextInputType.phone,
validator:
FormBuilderValidators.compose([]),
onChanged: (value) {
// setState(() {
// _areaValue = double.parse(value!);
// });
},
),
),
const SizedBox(
height: 40,
width: 40,
child: Center(
child: Text(
'%',
style: TextStyle(
fontSize: 18,
fontWeight: FontWeight.bold),
),
),
)
],
),
SizedBox(
height: 10,
),
Row(
children: [
Expanded(
flex: 1,
child: FormBuilderTextField(
name: 'areaValue',
decoration:
normalTextFieldStyle("Area", ""),
keyboardType: TextInputType.phone,
validator:
FormBuilderValidators.compose([]),
onChanged: (value) {
@ -358,56 +496,6 @@ class _AddExtraItemsOffline extends State<AddExtraItemsOffline> {
),
],
),
// const SizedBox(height: 10),
// FormBuilderTextField(
// name: 'depRate',
// decoration:
// normalTextFieldStyle("Depreciation Rate", ""),
// validator: FormBuilderValidators.compose([]),
// onChanged: (value) {
// setState(() {
// _depValue = double.parse(value!);
// });
// },
// ),
// const SizedBox(height: 10),
// FormBuilderTextField(
// name: 'marketValue',
// decoration: normalTextFieldStyle(
// NumberFormat.currency(
// locale: 'en-PH', symbol: "")
// .format(_totalMarketValue(_unitValue,
// _unitBase, _areaValue, _depValue)),
// ""),
// validator: FormBuilderValidators.compose([]),
// onChanged: (value) {
// setState(() {
// _marketValue = double.parse(value!);
// });
// },
// ),
// const SizedBox(height: 10),
// Text('Amount of Depreciation'),
// const SizedBox(height: 5),
// Container(
// height: 45.0,
// width: double.infinity,
// decoration: BoxDecoration(
// color: Colors.white,
// border: Border.all(
// color: Colors.grey,
// width: 1.0,
// ),
// borderRadius: BorderRadius.circular(5.0),
// ),
// child: Align(
// alignment: Alignment.center,
// child: Text(NumberFormat.currency(
// locale: 'en-PH', symbol: "")
// .format(_amountofDepreciation(_unitValue,
// _unitBase, _areaValue, _depValue)))),
// ),
Visibility(
visible: !_withoutBUCC,
child: Column(
@ -490,6 +578,8 @@ class _AddExtraItemsOffline extends State<AddExtraItemsOffline> {
child: FormBuilderTextField(
enabled: isSecondHand,
name: 'secondHandMat',
keyboardType:
TextInputType.phone,
textAlign: TextAlign.center,
decoration:
normalTextFieldStyle(
@ -533,7 +623,6 @@ class _AddExtraItemsOffline extends State<AddExtraItemsOffline> {
],
),
),
const SizedBox(height: 10),
const Text('Market Value'),
const SizedBox(height: 5),
@ -579,33 +668,33 @@ class _AddExtraItemsOffline extends State<AddExtraItemsOffline> {
final tempID = await SharedPreferences
.getInstance();
context
.read<
AdditionalItemsOfflineBloc>()
.add(AddAdditionalItems(
context.read<AdditionalItemsOfflineBloc>().add(
AddAdditionalItems(
id: 1,
bldgapprDetailsId: tempID.getInt(
'tempid')!,
bldgapprDetailsId:
tempID.getInt('tempid')!,
classId: _classId,
assessedById: widget
.offlineProfile.id
.toString(),
assessedByName:
widget
.offlineProfile.firstName!,
assessedByName: widget
.offlineProfile
.firstName!,
dateCreated: formatter,
dateModified: 'None',
className: _className,
structType: _structureType,
unitValue: _withoutBUCC ==
true
? 0
: _unitValue,
unitValue: _withoutBUCC == true
? 100
: _unitValue * 100,
baseUnitValue: _unitBase,
area: _areaValue,
marketValue: (_unitValue *
_unitBase) *
_areaValue,
marketValue:
_calculateMarketValue(
_unitValue,
_unitBase,
_areaValue,
_withoutBUCC),
depreciationRate: _depValue,
adjustedMarketVal:
_totalMarketValue(
@ -640,7 +729,7 @@ class _AddExtraItemsOffline extends State<AddExtraItemsOffline> {
}
},
style: ElevatedButton.styleFrom(
primary: Colors.black,
backgroundColor: Colors.black,
),
child: const Text("Submit"),
),
@ -659,7 +748,7 @@ class _AddExtraItemsOffline extends State<AddExtraItemsOffline> {
.add(const LoadAdditionalItems());
},
style: ElevatedButton.styleFrom(
primary: Colors.black,
backgroundColor: Colors.black,
),
child: const Text("Cancel"),
),
@ -668,7 +757,7 @@ class _AddExtraItemsOffline extends State<AddExtraItemsOffline> {
)
],
),
));
)); // Use your actual widget
}
return Container();
},

View File

@ -2,8 +2,12 @@ import 'package:flutter/material.dart';
import 'package:flutter_bloc/flutter_bloc.dart';
import 'package:flutter_form_builder/flutter_form_builder.dart';
import 'package:im_stepper/stepper.dart';
import 'package:shared_preferences/shared_preferences.dart';
import 'package:unit2/model/offline/offline_profile.dart';
import 'package:unit2/screens/offline/passo/building/add/building_and_structure.dart';
import 'package:unit2/screens/offline/passo/building/add/drawing_pad.dart';
import 'package:unit2/screens/offline/passo/building/add/flutter_painter.dart';
import 'package:unit2/screens/offline/passo/building/add/imagePicker.dart';
import 'package:unit2/screens/offline/passo/building/add/property_appraisal.dart';
import 'package:unit2/screens/offline/passo/building/add/property_assessment.dart';
import 'package:unit2/screens/offline/passo/building/add/property_owner_info.dart';
@ -29,7 +33,7 @@ class AddBuilding extends StatefulWidget {
class _AddBuilding extends State<AddBuilding> {
int activeStep = 0; // Initial step set to 5.
int upperBound = 6;
int upperBound = 7;
List<String> foundation = [];
List<String> column = [];
@ -39,6 +43,18 @@ class _AddBuilding extends State<AddBuilding> {
List<String> flooring = [];
List<String> walls = [];
bool foundationOthers = false;
bool columOthers = false;
bool beamsOthers = false;
bool tfOthers = false;
bool roofOthers = false;
bool flooringOthers = false;
bool wpOthers = false;
String bldgType = "";
String bldgKind = "Structure type";
String unitValue = "";
void PrevBtn() {
setState(() {
activeStep--;
@ -93,6 +109,66 @@ class _AddBuilding extends State<AddBuilding> {
});
}
void updateFoundationOthers(bool updatedOthers) {
setState(() {
foundationOthers = updatedOthers;
});
}
void updateColumOthers(bool updatedOthers) {
setState(() {
columOthers = updatedOthers;
});
}
void updateBeamsOthers(bool updatedOthers) {
setState(() {
beamsOthers = updatedOthers;
});
}
void updateTfOthers(bool updatedOthers) {
setState(() {
tfOthers = updatedOthers;
});
}
void updateRoofOthers(bool updatedOthers) {
setState(() {
roofOthers = updatedOthers;
});
}
void updateFlooringOthers(bool updatedOthers) {
setState(() {
flooringOthers = updatedOthers;
});
}
void updateWpOthers(bool updatedOthers) {
setState(() {
wpOthers = updatedOthers;
});
}
void updatedBldgType(dynamic updatedBldgType) {
setState(() {
bldgType = updatedBldgType;
});
}
void updatedBldgKind(dynamic updatedBldgKind) {
setState(() {
bldgKind = updatedBldgKind;
});
}
void updatedUnitValue(dynamic updatedUnitValue) {
setState(() {
unitValue = updatedUnitValue;
});
}
@override
Widget build(BuildContext context) {
print(widget.offlineProfile.toJson());
@ -114,7 +190,7 @@ class _AddBuilding extends State<AddBuilding> {
),
body: Column(children: [
NumberStepper(
numbers: [1, 2, 3, 4, 5, 6, 7, 8],
numbers: [1, 2, 3, 4, 5, 6, 7, 8, 9],
stepPadding: 5,
activeStepColor: primary,
numberStyle: TextStyle(color: Colors.white),
@ -162,40 +238,67 @@ class _AddBuilding extends State<AddBuilding> {
case 2:
return GeneralDescriptionOfflinePage(
NextBtn, PrevBtn, widget.offlineProfile);
NextBtn,
PrevBtn,
widget.offlineProfile,
bldgKind,
bldgType,
unitValue,
updatedUnitValue,
updatedBldgKind,
updatedBldgType);
case 3:
return FlutterDraw();
case 4:
return BuildingAndStructureOfflinePage(
PrevBtn, NextBtn, widget.offlineProfile);
case 4:
case 5:
return StatefulBuilder(
builder: (context, StateSetter setInnerState) =>
StructuralMaterialsOfflinePage(PrevBtn, NextBtn,
foundation: foundation,
column: column,
beam: beam,
trussFraming: trussFraming,
roof: roof,
flooring: flooring,
walls: walls,
updateFoundation: updateFoundation,
updateColumn: updateColumn,
updateBeam: updateBeam,
updateFlooring: updateFlooring,
updateRoof: updateRoof,
updateTrussFraming: updateTrussFraming,
updateWalls: updateWalls));
StructuralMaterialsOfflinePage(
PrevBtn,
NextBtn,
foundationOthers: foundationOthers,
columOthers: columOthers,
beamsOthers: beamsOthers,
tfOthers: tfOthers,
roofOthers: roofOthers,
flooringOthers: flooringOthers,
wpOthers: wpOthers,
foundation: foundation,
column: column,
beam: beam,
trussFraming: trussFraming,
roof: roof,
flooring: flooring,
walls: walls,
updateFoundation: updateFoundation,
updateColumn: updateColumn,
updateBeam: updateBeam,
updateFlooring: updateFlooring,
updateRoof: updateRoof,
updateTrussFraming: updateTrussFraming,
updateWalls: updateWalls,
updateFoundationOthers: updateFoundationOthers,
updateColumOthers: updateColumOthers,
updateBeamsOthers: updateBeamsOthers,
updateTfOthers: updateTfOthers,
updateRoofOthers: updateRoofOthers,
updateFlooringOthers: updateFlooringOthers,
updateWpOthers: updateWpOthers,
));
case 5:
case 6:
return AdditionalItemOfflinePage(
PrevBtn, NextBtn, widget.offlineProfile);
case 6:
case 7:
return PropertyAppraisalOfflinePage(
NextBtn, PrevBtn, widget.offlineProfile);
case 7:
case 8:
return PropertyAssessmentOfflinePage(
onCloseTransaction, widget.offlineProfile);
@ -204,8 +307,12 @@ class _AddBuilding extends State<AddBuilding> {
}
}
void onCloseTransaction() {
void onCloseTransaction() async {
final tempID = await SharedPreferences.getInstance();
Navigator.of(context).pop();
widget.triggerBlocEvent();
WidgetsBinding.instance.addPostFrameCallback((_) {
widget.triggerBlocEvent();
});
await tempID.setBool('floorSketchSaved', false);
}
}

View File

@ -0,0 +1,463 @@
import 'dart:async';
import 'dart:convert';
import 'dart:io';
import 'dart:ui' as ui;
import 'package:flutter/foundation.dart';
import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
import 'package:flutter_drawing_board/flutter_drawing_board.dart';
import 'package:flutter_drawing_board/paint_contents.dart';
import 'package:flutter_drawing_board/paint_extension.dart';
import 'package:path_provider/path_provider.dart';
import 'package:permission_handler/permission_handler.dart';
import 'package:unit2/utils/request_permission.dart';
import 'package:http/http.dart';
import 'package:unit2/utils/urls.dart'; // Removed 'as http'
// import 'test_data.dart';
Future<ui.Image> _getImage(String path) async {
final Completer<ImageInfo> completer = Completer<ImageInfo>();
final NetworkImage img = NetworkImage(path);
img.resolve(ImageConfiguration.empty).addListener(
ImageStreamListener((ImageInfo info, _) {
completer.complete(info);
}),
);
final ImageInfo imageInfo = await completer.future;
return imageInfo.image;
}
const Map<String, dynamic> _testLine1 = <String, dynamic>{
'type': 'StraightLine',
'startPoint': <String, dynamic>{
'dx': 68.94337550070736,
'dy': 62.05980083656557
},
'endPoint': <String, dynamic>{
'dx': 277.1373386828114,
'dy': 277.32029957032194
},
'paint': <String, dynamic>{
'blendMode': 3,
'color': 4294198070,
'filterQuality': 3,
'invertColors': false,
'isAntiAlias': false,
'strokeCap': 1,
'strokeJoin': 1,
'strokeWidth': 4.0,
'style': 1
}
};
const Map<String, dynamic> _testLine2 = <String, dynamic>{
'type': 'StraightLine',
'startPoint': <String, dynamic>{
'dx': 106.35164817830423,
'dy': 255.9575653134524
},
'endPoint': <String, dynamic>{
'dx': 292.76034659254094,
'dy': 92.125586665872
},
'paint': <String, dynamic>{
'blendMode': 3,
'color': 4294198070,
'filterQuality': 3,
'invertColors': false,
'isAntiAlias': false,
'strokeCap': 1,
'strokeJoin': 1,
'strokeWidth': 4.0,
'style': 1
}
};
/// Custom drawn triangles
class Triangle extends PaintContent {
Triangle();
Triangle.data({
required this.startPoint,
required this.A,
required this.B,
required this.C,
required Paint paint,
}) : super.paint(paint);
factory Triangle.fromJson(Map<String, dynamic> data) {
return Triangle.data(
startPoint: jsonToOffset(data['startPoint'] as Map<String, dynamic>),
A: jsonToOffset(data['A'] as Map<String, dynamic>),
B: jsonToOffset(data['B'] as Map<String, dynamic>),
C: jsonToOffset(data['C'] as Map<String, dynamic>),
paint: jsonToPaint(data['paint'] as Map<String, dynamic>),
);
}
Offset startPoint = Offset.zero;
Offset A = Offset.zero;
Offset B = Offset.zero;
Offset C = Offset.zero;
@override
void startDraw(Offset startPoint) => this.startPoint = startPoint;
@override
void drawing(Offset nowPoint) {
A = Offset(
startPoint.dx + (nowPoint.dx - startPoint.dx) / 2, startPoint.dy);
B = Offset(startPoint.dx, nowPoint.dy);
C = nowPoint;
}
@override
void draw(Canvas canvas, Size size, bool deeper) {
final Path path = Path()
..moveTo(A.dx, A.dy)
..lineTo(B.dx, B.dy)
..lineTo(C.dx, C.dy)
..close();
canvas.drawPath(path, paint);
}
@override
Triangle copy() => Triangle();
@override
Map<String, dynamic> toContentJson() {
return <String, dynamic>{
'startPoint': startPoint.toJson(),
'A': A.toJson(),
'B': B.toJson(),
'C': C.toJson(),
'paint': paint.toJson(),
};
}
}
/// Custom drawn image
/// url: https://web-strapi.mrmilu.com/uploads/flutter_logo_470e9f7491.png
const String _imageUrl =
'https://web-strapi.mrmilu.com/uploads/flutter_logo_470e9f7491.png';
class ImageContent extends PaintContent {
ImageContent(this.image, {this.imageUrl = ''});
ImageContent.data({
required this.startPoint,
required this.size,
required this.image,
required this.imageUrl,
required Paint paint,
}) : super.paint(paint);
factory ImageContent.fromJson(Map<String, dynamic> data) {
return ImageContent.data(
startPoint: jsonToOffset(data['startPoint'] as Map<String, dynamic>),
size: jsonToOffset(data['size'] as Map<String, dynamic>),
imageUrl: data['imageUrl'] as String,
image: data['image'] as ui.Image,
paint: jsonToPaint(data['paint'] as Map<String, dynamic>),
);
}
Offset startPoint = Offset.zero;
Offset size = Offset.zero;
final String imageUrl;
final ui.Image image;
@override
void startDraw(Offset startPoint) => this.startPoint = startPoint;
@override
void drawing(Offset nowPoint) => size = nowPoint - startPoint;
@override
void draw(Canvas canvas, Size size, bool deeper) {
final Rect rect = Rect.fromPoints(startPoint, startPoint + this.size);
paintImage(canvas: canvas, rect: rect, image: image, fit: BoxFit.fill);
}
@override
ImageContent copy() => ImageContent(image);
@override
Map<String, dynamic> toContentJson() {
return <String, dynamic>{
'startPoint': startPoint.toJson(),
'size': size.toJson(),
'imageUrl': imageUrl,
'paint': paint.toJson(),
};
}
}
class DrawingScreen extends StatelessWidget {
const DrawingScreen({Key? key}) : super(key: key);
@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'Drawing Test',
theme: ThemeData(primarySwatch: Colors.blue),
home: const MyHomePage(),
);
}
}
class MyHomePage extends StatefulWidget {
const MyHomePage({Key? key}) : super(key: key);
@override
State<MyHomePage> createState() => _MyHomePageState();
}
class _MyHomePageState extends State<MyHomePage> {
///
final DrawingController _drawingController = DrawingController();
final TransformationController _transformationController =
TransformationController();
final GlobalKey _repaintBoundaryKey = GlobalKey();
File? _image;
final String imagePath = '/data/user/0/com.app.rpass/cache/182.png';
@override
void dispose() {
_drawingController.dispose();
super.dispose();
}
/// `getImageData()`
Future<void> _getImageData() async {
final Uint8List? data =
(await _drawingController.getImageData())?.buffer.asUint8List();
if (data == null) {
debugPrint('获取图片数据失败');
return;
}
if (mounted) {
showDialog<void>(
context: context,
builder: (BuildContext c) {
return Material(
color: Colors.transparent,
child: InkWell(
onTap: () => Navigator.pop(c), child: Image.memory(data)),
);
},
);
}
}
Future<String> _saveImageToDevice(Uint8List data) async {
// Get the temporary directory
final directory = await getTemporaryDirectory();
final tempDirectory = directory.path;
// Create a file path in the temporary directory
final filePath = '$tempDirectory/181.png';
final file = File(filePath);
// Write the image bytes to the file
await file.writeAsBytes(data);
// Return the file path
print(filePath);
return filePath;
}
Future<void> _saveAndShowImage() async {
final Uint8List? data =
(await _drawingController.getImageData())?.buffer.asUint8List();
if (data == null) {
debugPrint('Failed to get image data');
return;
}
final path = await _saveImageToDevice(data);
if (mounted) {
showDialog<void>(
context: context,
builder: (BuildContext c) {
return Material(
color: Colors.transparent,
child: InkWell(
onTap: () => Navigator.pop(c), child: Image.memory(data)),
);
},
);
ScaffoldMessenger.of(context).showSnackBar(
SnackBar(content: Text('Image saved to $path')),
);
}
}
Future<void> _showImage() async {
showDialog<void>(
context: context,
builder: (BuildContext c) {
return Material(
color: Colors.transparent,
child: InkWell(
onTap: () => Navigator.pop(c),
child:
Image.file(File('/data/user/0/com.app.rpass/cache/img.png'))),
);
},
);
}
void _restBoard() {
_transformationController.value = Matrix4.identity();
}
Future<Response> _postBuildingDetails(Map<String, dynamic> details) async {
String xClientKey = "unitK3CQaXiWlPReDsBzmmwBZPd9Re1z";
String xClientKeySecret = "unitcYqAN7GGalyz";
// Construct the headers for the request
Map<String, String> headers = {
'Content-Type': 'multipart/form-data',
'X-Client-Key': xClientKey,
'X-Client-Secret': xClientKeySecret,
};
// Create a MultipartRequest
var request = MultipartRequest(
'POST',
Uri.parse(
'https://${Url.instance.host()}/api/rptass_app/bldgappr_sketch/'),
);
// Add the headers to the request
request.headers.addAll(headers);
// Add JSON data as a field
// Add individual fields to the request
details.forEach((key, value) {
request.fields[key] = value.toString();
});
var file = File(imagePath);
// Add the floor sketch image file, if it exists
request.files.add(
await MultipartFile.fromPath(
'floor_sketch', // Field name in the API
file.path,
filename: file.path,
),
);
// Send the request and get the response
var streamedResponse = await request.send();
return await Response.fromStream(streamedResponse);
}
Future<void> _uploadImage() async {
// Create a map with the required fields
var file = File(imagePath);
Map<String, dynamic> detailsMap = {
"bldgappr_details_id": 182, // int8 NOT NULL
"date_created": DateTime.now().toIso8601String(), // timestamptz NULL
"floor_sketch": file.path, // text NULL
"gen_code": "5TH", // varchar(20) NOT NULL
};
try {
Response response = await _postBuildingDetails(detailsMap);
print(response.body);
if (response.statusCode == 201) {
print('Upload successful');
} else {
print('Upload failed with status: ${response.statusCode}');
}
} catch (e) {
print('Error: $e');
}
}
@override
Widget build(BuildContext context) {
return Scaffold(
resizeToAvoidBottomInset: false,
backgroundColor: Colors.white,
body: Column(
children: <Widget>[
Row(
mainAxisAlignment: MainAxisAlignment.end,
children: [
IconButton(
icon: const Icon(Icons.delete_rounded),
color: Colors.red,
iconSize: 38,
tooltip: 'Open shopping cart',
onPressed: () {
_showImage();
},
),
IconButton(
icon: const Icon(Icons.check_circle),
color: Colors.red,
iconSize: 35,
tooltip: 'Open shopping cart',
onPressed: () {
_saveAndShowImage();
},
),
],
),
Expanded(
child: LayoutBuilder(
builder: (BuildContext context, BoxConstraints constraints) {
return RepaintBoundary(
key: _repaintBoundaryKey,
child: DrawingBoard(
// boardPanEnabled: false,
// boardScaleEnabled: false,
transformationController: _transformationController,
controller: _drawingController,
background: Container(
width: constraints.maxWidth,
height: constraints.maxHeight,
color: Colors.grey,
),
showDefaultActions: true,
showDefaultTools: true,
defaultToolsBuilder: (Type t, _) {
return DrawingBoard.defaultTools(t, _drawingController)
..insert(
1,
DefToolItem(
icon: Icons.change_history_rounded,
isActive: t == Triangle,
onTap: () =>
_drawingController.setPaintContent(Triangle()),
),
);
},
),
);
},
),
),
],
),
);
}
}

View File

@ -0,0 +1,818 @@
import 'dart:async';
import 'dart:io';
import 'dart:ui';
import 'package:http/http.dart'; // Removed 'as http'
import 'package:path/path.dart'; // For basename function
import 'dart:convert';
import 'package:flutter/foundation.dart';
import 'package:flutter/material.dart';
import 'package:flutter_painter_v2/flutter_painter.dart';
import 'package:flutter_painter_v2/flutter_painter_extensions.dart';
import 'package:flutter_painter_v2/flutter_painter_pure.dart';
import 'package:path_provider/path_provider.dart';
import 'dart:ui' as ui;
import 'package:phosphor_flutter/phosphor_flutter.dart';
import 'package:shared_preferences/shared_preferences.dart';
import 'package:unit2/model/passo/floor_sketch.dart';
import 'package:unit2/utils/urls.dart';
import '../../../../../sevices/offline/offline_passo/admin/sql_services/sql_services.dart';
class FlutterDraw extends StatefulWidget {
const FlutterDraw({Key? key}) : super(key: key);
@override
_FlutterPainterExampleState createState() => _FlutterPainterExampleState();
}
class _FlutterPainterExampleState extends State<FlutterDraw> {
static const Color red = Color.fromARGB(255, 0, 0, 0);
FocusNode textFocusNode = FocusNode();
late PainterController controller;
ui.Image? backgroundImage;
Paint shapePaint = Paint()
..strokeWidth = 5
..color = Colors.black
..style = PaintingStyle.stroke
..strokeCap = StrokeCap.round;
File? _image;
final String imagePath = '/data/user/0/com.app.rpass/cache/182.png';
static const List<String> imageLinks = [
"https://i.imgur.com/btoI5OX.png",
"https://i.imgur.com/EXTQFt7.png",
"https://i.imgur.com/EDNjJYL.png",
"https://i.imgur.com/uQKD6NL.png",
"https://i.imgur.com/cMqVRbl.png",
"https://i.imgur.com/1cJBAfI.png",
"https://i.imgur.com/eNYfHKL.png",
"https://i.imgur.com/c4Ag5yt.png",
"https://i.imgur.com/GhpCJuf.png",
"https://i.imgur.com/XVMeluF.png",
"https://i.imgur.com/mt2yO6Z.png",
"https://i.imgur.com/rw9XP1X.png",
"https://i.imgur.com/pD7foZ8.png",
"https://i.imgur.com/13Y3vp2.png",
"https://i.imgur.com/ojv3yw1.png",
"https://i.imgur.com/f8ZNJJ7.png",
"https://i.imgur.com/BiYkHzw.png",
"https://i.imgur.com/snJOcEz.png",
"https://i.imgur.com/b61cnhi.png",
"https://i.imgur.com/FkDFzYe.png",
"https://i.imgur.com/P310x7d.png",
"https://i.imgur.com/5AHZpua.png",
"https://i.imgur.com/tmvJY4r.png",
"https://i.imgur.com/PdVfGkV.png",
"https://i.imgur.com/1PRzwBf.png",
"https://i.imgur.com/VeeMfBS.png",
];
@override
void initState() {
super.initState();
controller = PainterController(
settings: PainterSettings(
text: TextSettings(
focusNode: textFocusNode,
textStyle: const TextStyle(
fontWeight: FontWeight.bold, color: red, fontSize: 18),
),
freeStyle: const FreeStyleSettings(
color: red,
strokeWidth: 5,
),
shape: ShapeSettings(
paint: shapePaint,
),
scale: const ScaleSettings(
enabled: true,
minScale: 1,
maxScale: 5,
)));
// Listen to focus events of the text field
textFocusNode.addListener(onFocus);
// Initialize background
initBackground();
}
/// Fetches image from an [ImageProvider] (in this example, [NetworkImage])
/// to use it as a background
void initBackground() async {
final prefs = await SharedPreferences.getInstance();
final floorSketchSaved = prefs.getBool('floorSketchSaved') ?? false;
final tempID = prefs.getInt('tempid');
print(floorSketchSaved);
ui.Image image;
if (floorSketchSaved && tempID != null) {
final String imagePath = '/data/user/0/com.app.rpass/cache/$tempID.png';
image = await _loadImageFromPath(imagePath);
} else {
image = await const AssetImage('assets/pngs/white_bg.png').image;
}
setState(() {
backgroundImage = image;
controller.background = image.backgroundDrawable;
});
}
/// Updates UI when the focus changes
void onFocus() {
setState(() {});
}
Future<ui.Image> _loadImageFromPath(String imagePath) async {
final file = File(imagePath);
final bytes = await file.readAsBytes();
final Completer<ui.Image> completer = Completer();
ui.decodeImageFromList(bytes, (ui.Image img) {
completer.complete(img);
});
return completer.future;
}
Future<void> deleteImage(BuildContext context) async {
final prefs = await SharedPreferences.getInstance();
final tempID = prefs.getInt('tempid');
if (tempID != null) {
final String imagePath = '/data/user/0/com.app.rpass/cache/$tempID.png';
final file = File(imagePath);
if (await file.exists()) {
await file.delete();
ScaffoldMessenger.of(context).showSnackBar(
SnackBar(content: Text('Image deleted successfully')),
);
final image = await const AssetImage('assets/pngs/white_bg.png').image;
setState(() {
backgroundImage = image;
controller.background = image.backgroundDrawable;
});
} else {
ScaffoldMessenger.of(context).showSnackBar(
SnackBar(content: Text('Image does not exist')),
);
}
}
}
Widget buildDefault(BuildContext context) {
return Scaffold(
appBar: PreferredSize(
preferredSize: const Size(double.infinity, kToolbarHeight),
// Listen to the controller and update the UI when it updates.
child: ValueListenableBuilder<PainterControllerValue>(
valueListenable: controller,
builder: (context, _, child) {
return AppBar(
title: child,
automaticallyImplyLeading: false, // Disable the back button
actions: [
// Delete the selected drawable
IconButton(
icon: const Icon(
PhosphorIcons.trash,
),
onPressed: controller.selectedObjectDrawable == null
? null
: removeSelectedDrawable,
),
// Delete the selected drawable
IconButton(
icon: const Icon(
Icons.flip,
),
onPressed: controller.selectedObjectDrawable != null &&
controller.selectedObjectDrawable is ImageDrawable
? flipSelectedImageDrawable
: null,
),
// Redo action
IconButton(
icon: const Icon(
PhosphorIcons.arrowClockwise,
),
onPressed: controller.canRedo ? redo : null,
),
// Undo action
IconButton(
icon: const Icon(
PhosphorIcons.arrowCounterClockwise,
),
onPressed: controller.canUndo ? undo : null,
),
],
);
}),
),
// Generate image
floatingActionButton: Stack(
children: <Widget>[
Align(
alignment: Alignment.bottomRight,
child: FloatingActionButton(
heroTag: 'btn1',
child: const Icon(
PhosphorIcons.imageFill,
),
onPressed: () => renderAndDisplayImage(context),
),
),
Align(
alignment: Alignment.bottomRight,
child: Padding(
padding: const EdgeInsets.only(bottom: 60.0),
child: FloatingActionButton(
heroTag: 'btn2',
child: const Icon(
Icons.delete,
),
onPressed: () => deleteImage(context),
),
),
),
// Add more FloatingActionButton widgets here if needed
],
),
body: Stack(
children: [
if (backgroundImage != null)
// Enforces constraints
Positioned.fill(
child: Center(
child: AspectRatio(
aspectRatio:
backgroundImage!.width / backgroundImage!.height,
child: FlutterPainter(
controller: controller,
),
),
),
),
Positioned(
bottom: 0,
right: 0,
left: 0,
child: ValueListenableBuilder(
valueListenable: controller,
builder: (context, _, __) => Row(
mainAxisAlignment: MainAxisAlignment.center,
children: [
Flexible(
child: Container(
constraints: const BoxConstraints(
maxWidth: 400,
),
padding: const EdgeInsets.symmetric(horizontal: 15),
decoration: const BoxDecoration(
borderRadius:
BorderRadius.vertical(top: Radius.circular(20)),
color: Colors.white54,
),
child: Column(
mainAxisSize: MainAxisSize.min,
children: [
if (controller.freeStyleMode !=
FreeStyleMode.none) ...[
const Divider(),
const Text("Free Style Settings"),
// Control free style stroke width
Row(
children: [
const Expanded(
flex: 1, child: Text("Stroke Width")),
Expanded(
flex: 3,
child: Slider.adaptive(
min: 2,
max: 25,
value: controller.freeStyleStrokeWidth,
onChanged: setFreeStyleStrokeWidth),
),
],
),
if (controller.freeStyleMode ==
FreeStyleMode.draw)
Row(
children: [
const Expanded(
flex: 1, child: Text("Color")),
// Control free style color hue
Expanded(
flex: 3,
child: Slider.adaptive(
min: 0,
max: 359.99,
value: HSVColor.fromColor(
controller.freeStyleColor)
.hue,
activeColor:
controller.freeStyleColor,
onChanged: setFreeStyleColor),
),
],
),
],
if (textFocusNode.hasFocus) ...[
const Divider(),
const Text("Text settings"),
// Control text font size
Row(
children: [
const Expanded(
flex: 1, child: Text("Font Size")),
Expanded(
flex: 3,
child: Slider.adaptive(
min: 8,
max: 96,
value:
controller.textStyle.fontSize ?? 14,
onChanged: setTextFontSize),
),
],
),
// Control text color hue
Row(
children: [
const Expanded(flex: 1, child: Text("Color")),
Expanded(
flex: 3,
child: Slider.adaptive(
min: 0,
max: 359.99,
value: HSVColor.fromColor(
controller.textStyle.color ??
red)
.hue,
activeColor: controller.textStyle.color,
onChanged: setTextColor),
),
],
),
],
if (controller.shapeFactory != null) ...[
const Divider(),
const Text("Shape Settings"),
// Control text color hue
Row(
children: [
const Expanded(
flex: 1, child: Text("Stroke Width")),
Expanded(
flex: 3,
child: Slider.adaptive(
min: 2,
max: 25,
value: controller
.shapePaint?.strokeWidth ??
shapePaint.strokeWidth,
onChanged: (value) =>
setShapeFactoryPaint(
(controller.shapePaint ??
shapePaint)
.copyWith(
strokeWidth: value,
))),
),
],
),
// Control shape color hue
Row(
children: [
const Expanded(flex: 1, child: Text("Color")),
Expanded(
flex: 3,
child: Slider.adaptive(
min: 0,
max: 359.99,
value: HSVColor.fromColor(
(controller.shapePaint ??
shapePaint)
.color)
.hue,
activeColor: (controller.shapePaint ??
shapePaint)
.color,
onChanged: (hue) =>
setShapeFactoryPaint(
(controller.shapePaint ??
shapePaint)
.copyWith(
color: HSVColor.fromAHSV(
1, hue, 1, 1)
.toColor(),
))),
),
],
),
Row(
children: [
const Expanded(
flex: 1, child: Text("Fill shape")),
Expanded(
flex: 3,
child: Center(
child: Switch(
value: (controller.shapePaint ??
shapePaint)
.style ==
PaintingStyle.fill,
onChanged: (value) =>
setShapeFactoryPaint(
(controller.shapePaint ??
shapePaint)
.copyWith(
style: value
? PaintingStyle.fill
: PaintingStyle.stroke,
))),
),
),
],
),
]
],
),
),
),
],
),
),
),
],
),
bottomNavigationBar: ValueListenableBuilder(
valueListenable: controller,
builder: (context, _, __) => Row(
mainAxisAlignment: MainAxisAlignment.spaceAround,
children: [
// Free-style eraser
IconButton(
icon: Icon(
PhosphorIcons.eraser,
color: controller.freeStyleMode == FreeStyleMode.erase
? Theme.of(context).primaryColor
: null,
),
onPressed: toggleFreeStyleErase,
),
// Free-style drawing
IconButton(
icon: Icon(
PhosphorIcons.scribbleLoop,
color: controller.freeStyleMode == FreeStyleMode.draw
? Theme.of(context).primaryColor
: null,
),
onPressed: toggleFreeStyleDraw,
),
// Add text
IconButton(
icon: Icon(
PhosphorIcons.textT,
color: textFocusNode.hasFocus
? Theme.of(context).primaryColor
: null,
),
onPressed: addText,
),
// Add sticker image
IconButton(
icon: const Icon(
PhosphorIcons.sticker,
),
onPressed: () => addSticker(context),
),
// Add shapes
if (controller.shapeFactory == null)
PopupMenuButton<ShapeFactory?>(
tooltip: "Add shape",
itemBuilder: (context) => <ShapeFactory, String>{
LineFactory(): "Line",
ArrowFactory(): "Arrow",
DoubleArrowFactory(): "Double Arrow",
RectangleFactory(): "Rectangle",
OvalFactory(): "Oval",
}
.entries
.map((e) => PopupMenuItem(
value: e.key,
child: Row(
mainAxisAlignment: MainAxisAlignment.start,
children: [
Icon(
getShapeIcon(e.key),
color: Colors.black,
),
Text(" ${e.value}")
],
)))
.toList(),
onSelected: selectShape,
child: Padding(
padding: const EdgeInsets.all(8.0),
child: Icon(
getShapeIcon(controller.shapeFactory),
color: controller.shapeFactory != null
? Theme.of(context).primaryColor
: null,
),
),
)
else
IconButton(
icon: Icon(
getShapeIcon(controller.shapeFactory),
color: Theme.of(context).primaryColor,
),
onPressed: () => selectShape(null),
),
],
),
));
}
@override
Widget build(BuildContext context) {
return buildDefault(context);
}
static IconData getShapeIcon(ShapeFactory? shapeFactory) {
if (shapeFactory is LineFactory) return PhosphorIcons.lineSegment;
if (shapeFactory is ArrowFactory) return PhosphorIcons.arrowUpRight;
if (shapeFactory is DoubleArrowFactory) {
return PhosphorIcons.arrowsHorizontal;
}
if (shapeFactory is RectangleFactory) return PhosphorIcons.rectangle;
if (shapeFactory is OvalFactory) return PhosphorIcons.circle;
return PhosphorIcons.polygon;
}
void undo() {
controller.undo();
}
void redo() {
controller.redo();
}
void toggleFreeStyleDraw() {
controller.freeStyleMode = controller.freeStyleMode != FreeStyleMode.draw
? FreeStyleMode.draw
: FreeStyleMode.none;
}
void toggleFreeStyleErase() {
controller.freeStyleMode = controller.freeStyleMode != FreeStyleMode.erase
? FreeStyleMode.erase
: FreeStyleMode.none;
}
void addText() {
if (controller.freeStyleMode != FreeStyleMode.none) {
controller.freeStyleMode = FreeStyleMode.none;
}
controller.addText();
}
void addSticker(BuildContext context) async {
final imageLink = await showDialog<String>(
context: context,
builder: (context) => const SelectStickerImageDialog(
imagesLinks: imageLinks,
));
if (imageLink == null) return;
controller.addImage(
await NetworkImage(imageLink).image, const Size(100, 100));
}
void setFreeStyleStrokeWidth(double value) {
controller.freeStyleStrokeWidth = value;
}
void setFreeStyleColor(double hue) {
controller.freeStyleColor = HSVColor.fromAHSV(1, hue, 1, 1).toColor();
}
void setTextFontSize(double size) {
// Set state is just to update the current UI, the [FlutterPainter] UI updates without it
setState(() {
controller.textSettings = controller.textSettings.copyWith(
textStyle:
controller.textSettings.textStyle.copyWith(fontSize: size));
});
}
void setShapeFactoryPaint(Paint paint) {
// Set state is just to update the current UI, the [FlutterPainter] UI updates without it
setState(() {
controller.shapePaint = paint;
});
}
void setTextColor(double hue) {
controller.textStyle = controller.textStyle
.copyWith(color: HSVColor.fromAHSV(1, hue, 1, 1).toColor());
}
void selectShape(ShapeFactory? factory) {
controller.shapeFactory = factory;
}
Future<void> _uploadImage() async {
// Create a map with the required fields
final tempID = await SharedPreferences.getInstance();
final tempIDS = tempID.getInt('tempid');
final String imagePath = '/data/user/0/com.app.rpass/cache/$tempIDS.png';
await tempID.setBool('floorSketchSaved', true);
var file = File(imagePath);
// Map<String, dynamic> detailsMap = {
// "bldgappr_details_id": 182, // int8 NOT NULL
// "date_created": DateTime.now().toIso8601String(), // timestamptz NULL
// "floor_sketch": file.path, // text NULL
// "gen_code": "5TH", // varchar(20) NOT NULL
// };
var floorSketchs = FloorSketch(
bldgapprDetailsId: tempIDS,
dateCreated: DateTime.now().toIso8601String(),
floorSketch: file.path,
genCode: "5TH");
try {
// Response response = await _postBuildingDetails(detailsMap);
// print(response.body);
await SQLServices.instance.createFloorSketch(floorSketchs);
// if (response.statusCode == 201) {
// print('Upload successful');
// } else {
// print('Upload failed with status: ${response.statusCode}');
// }
} catch (e) {
if (kDebugMode) {
print('Error: $e');
}
}
}
void renderAndDisplayImage(BuildContext context) async {
if (backgroundImage == null) return;
final backgroundImageSize = Size(
backgroundImage!.width.toDouble(),
backgroundImage!.height.toDouble(),
);
try {
// Render the image
final image = await controller.renderImage(backgroundImageSize);
final byteData = await image.toByteData(format: ui.ImageByteFormat.png);
final imageBytes = byteData!.buffer.asUint8List();
final tempID = await SharedPreferences.getInstance();
final tempIDS = tempID.getInt('tempid');
// Write the PNG image data to a file
final file = File('${(await getTemporaryDirectory()).path}/$tempIDS.png');
await file.writeAsBytes(imageBytes);
// Show a dialog with the image
// ignore: use_build_context_synchronously
showDialog(
context: context,
builder: (BuildContext context) => AlertDialog(
title: const Text('Rendered Image'),
content: Image.memory(imageBytes),
actions: <Widget>[
TextButton(
child: const Text('SAVE'),
onPressed: () {
_uploadImage();
},
),
TextButton(
child: const Text('Close'),
onPressed: () {
Navigator.of(context).pop();
},
),
],
),
);
// Show a snackbar with the file path
// ignore: use_build_context_synchronously
ScaffoldMessenger.of(context).showSnackBar(
SnackBar(content: Text('Image saved to ${file.path}')),
);
} catch (e) {
// Handle potential errors
// ignore: use_build_context_synchronously
ScaffoldMessenger.of(context).showSnackBar(
SnackBar(content: Text('Error: $e')),
);
}
}
void removeSelectedDrawable() {
final selectedDrawable = controller.selectedObjectDrawable;
if (selectedDrawable != null) controller.removeDrawable(selectedDrawable);
}
void flipSelectedImageDrawable() {
final imageDrawable = controller.selectedObjectDrawable;
if (imageDrawable is! ImageDrawable) return;
controller.replaceDrawable(
imageDrawable, imageDrawable.copyWith(flipped: !imageDrawable.flipped));
}
}
class RenderedImageDialog extends StatelessWidget {
final Future<Uint8List?> imageFuture;
final String imagePath = '/data/user/0/com.app.rpass/cache/182.png';
const RenderedImageDialog({Key? key, required this.imageFuture})
: super(key: key);
@override
Widget build(BuildContext context) {
return AlertDialog(
title: const Text("Rendered Image"),
content: FutureBuilder<Uint8List?>(
future: imageFuture,
builder: (context, snapshot) {
if (snapshot.connectionState != ConnectionState.done) {
return const SizedBox(
height: 50,
child: Center(child: CircularProgressIndicator.adaptive()),
);
}
if (!snapshot.hasData || snapshot.data == null) {
return const SizedBox();
}
return InteractiveViewer(
maxScale: 10, child: Image.memory(snapshot.data!));
},
),
);
}
}
class SelectStickerImageDialog extends StatelessWidget {
final List<String> imagesLinks;
const SelectStickerImageDialog({Key? key, this.imagesLinks = const []})
: super(key: key);
@override
Widget build(BuildContext context) {
return AlertDialog(
title: const Text("Select sticker"),
content: imagesLinks.isEmpty
? const Text("No images")
: FractionallySizedBox(
heightFactor: 0.5,
child: SingleChildScrollView(
child: Wrap(
children: [
for (final imageLink in imagesLinks)
InkWell(
onTap: () => Navigator.pop(context, imageLink),
child: FractionallySizedBox(
widthFactor: 1 / 4,
child: Image.network(imageLink),
),
),
],
),
),
),
actions: [
TextButton(
child: const Text("Cancel"),
onPressed: () => Navigator.pop(context),
)
],
);
}
}

View File

@ -1,3 +1,4 @@
import 'dart:convert';
import 'dart:ui';
import 'package:flutter/material.dart';
import 'package:flutter_bloc/flutter_bloc.dart';
@ -23,8 +24,24 @@ class GeneralDescriptionOfflinePage extends StatefulWidget {
final VoidCallback gendescPrevBtn;
final OfflineProfile offlineProfile;
final String bldgKind;
final String bldgType;
final String unitValue;
final Function(String) updatedUnitValue;
final Function(String) updatedBldgKind;
final Function(String) updatedBldgType;
GeneralDescriptionOfflinePage(
this.onPutGeneralDescription, this.gendescPrevBtn, this.offlineProfile);
this.onPutGeneralDescription,
this.gendescPrevBtn,
this.offlineProfile,
this.bldgKind,
this.bldgType,
this.unitValue,
this.updatedUnitValue,
this.updatedBldgKind,
this.updatedBldgType);
@override
_GeneralDescriptionOfflinePage createState() =>
@ -51,10 +68,6 @@ class _GeneralDescriptionOfflinePage
: now = DateTime.now(),
formatter = DateFormat.yMMMMd('en_US').format(DateTime.now());
late String bldgType;
late String bldgKind;
late String unitValue;
@override
Widget build(BuildContext context) {
return BlocConsumer<UnitConstructionAdminBloc, UnitConstructionAdminState>(
@ -99,23 +112,31 @@ class _GeneralDescriptionOfflinePage
errorText: "This field is required"),
searchInputDecoration:
normalTextFieldStyle("Structure Type", "").copyWith(
normalTextFieldStyle(widget.bldgKind, "").copyWith(
suffixIcon: const Icon(Icons.arrow_drop_down)),
////agency suggestion tap
focusNode: focus,
suggestionState: Suggestion.expand,
onSuggestionTap: (unit) {
onSuggestionTap: (unit) async {
setState(() {
bldgKind =
'${unit.item!.bldgType} - ${unit.item!.building}';
bldgType =
'${unit.item!.bldgType} - ${unit.item!.building}';
unitValue = unit.item!.unitValue;
widget.updatedBldgKind(
'${unit.item!.bldgType} - ${unit.item!.building}');
widget.updatedBldgType(
'${unit.item!.bldgType} - ${unit.item!.building}');
widget.updatedUnitValue(unit.item!.unitValue);
offlineBldgKey.currentState!
.patchValue({'bldg_type': unit.item});
});
// Save the selected UnitConstruct to SharedPreferences
SharedPreferences prefs =
await SharedPreferences.getInstance();
String jsonString = jsonEncode(unit.item!.toJson());
await prefs.setString(
'selected_bldg_type', jsonString);
// Unfocus the current focus node
focus.unfocus();
},
),
@ -128,8 +149,8 @@ class _GeneralDescriptionOfflinePage
children: <Widget>[
Expanded(
flex: 1,
child: customTextField(
"Bldg. Permit No.", "", 'bldg_permit'),
child: customTextField("Bldg. Permit No.", "",
'bldg_permit', TextInputType.number),
),
const SizedBox(width: 10.0),
Expanded(
@ -187,45 +208,47 @@ class _GeneralDescriptionOfflinePage
children: <Widget>[
Expanded(
flex: 1,
child: customTextField("Bldg. Age", "", 'bldg_age'),
child: customTextField("Bldg. Age", "", 'bldg_age',
TextInputType.number),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField(
"No. of storeys", "", 'no_of_storeys'))
child: customTextField("No. of storeys", "",
'no_of_storeys', TextInputType.number))
]),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField(
"Area of 1st Floor", "", 'area_of_1stFl'),
child: customTextField("Area of 1st Floor", "",
'area_of_1stFl', TextInputType.number),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField(
"Area of 2nd Floor", "", 'area_of_2ndFl'))
child: customTextField("Area of 2nd Floor", "",
'area_of_2ndFl', TextInputType.number))
]),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField(
"Area of 3rd Floor", "", 'area_of_3rdFl')),
child: customTextField("Area of 3rd Floor", "",
'area_of_3rdFl', TextInputType.number)),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField(
"Area of 4th Floor", "", 'area_of_4thFl'))
child: customTextField("Area of 4th Floor", "",
'area_of_4thFl', TextInputType.number))
]),
customTextField("Total Area", "", 'total_area'),
customTextField(
"Total Area", "", 'total_area', TextInputType.number),
SizedBox(
height: 50,
),
@ -259,36 +282,36 @@ class _GeneralDescriptionOfflinePage
widget.offlineProfile.firstName!,
dateCreated: formatter,
dateModified: 'None',
bldgKind: bldgKind ?? "",
strucType: bldgType ?? "",
bldgPermit: offlineBldgKey
.currentState?.value['bldg_permit'] ??
"",
bldgKind: widget.bldgKind ?? "",
strucType: widget.bldgType ?? "",
bldgPermit:
offlineBldgKey.currentState?.value['bldg_permit'] ??
" ",
dateIssued: offlineBldgKey
.currentState!.value['date_issued']
.toString() ??
"",
" ",
cct: 'None',
certCompletionIssued: offlineBldgKey
.currentState!.value['coc_issued']
.toString() ??
"",
" ",
certOccupancyIssued: offlineBldgKey
.currentState!.value['coo_issued']
.toString() ??
"",
" ",
dateCompleted: offlineBldgKey.currentState!.value['date_cnstructed'].toString() ?? "",
dateOccupied: offlineBldgKey.currentState!.value['date_occupied'].toString() ?? "",
bldgAge: offlineBldgKey.currentState!.value['bldg_age'] ?? "",
noStoreys: offlineBldgKey.currentState!.value['no_of_storeys'] ?? "",
area1Stfloor: offlineBldgKey.currentState!.value['area_of_1stFl'] ?? "",
area2Ndfloor: offlineBldgKey.currentState!.value['area_of_2ndFl'] ?? "",
area3Rdfloor: offlineBldgKey.currentState!.value['area_of_3rdFl'] ?? "",
area4Thfloor: offlineBldgKey.currentState!.value['area_of_4thFl'] ?? "",
totalFloorArea: offlineBldgKey.currentState?.value['total_area'] ?? "",
bldgAge: offlineBldgKey.currentState!.value['bldg_age'] ?? "0",
noStoreys: offlineBldgKey.currentState!.value['no_of_storeys'] ?? "0",
area1Stfloor: offlineBldgKey.currentState!.value['area_of_1stFl'] ?? "0",
area2Ndfloor: offlineBldgKey.currentState!.value['area_of_2ndFl'] ?? "0",
area3Rdfloor: offlineBldgKey.currentState!.value['area_of_3rdFl'] ?? "0",
area4Thfloor: offlineBldgKey.currentState!.value['area_of_4thFl'] ?? "0",
totalFloorArea: offlineBldgKey.currentState?.value['total_area'] ?? "0",
floorSketch: null,
actualUse: offlineBldgKey.currentState?.value['actual_use'] ?? "",
unitValue: unitValue ?? "",
unitValue: widget.unitValue ?? "",
genCode: '5th'));
widget.onPutGeneralDescription();
}

View File

@ -0,0 +1,129 @@
import 'package:flutter/material.dart';
import 'package:image_picker/image_picker.dart';
import 'package:http/http.dart'; // Removed 'as http'
import 'package:path/path.dart'; // For basename function
import 'dart:convert';
import 'dart:io';
import 'package:unit2/model/location/purok.dart';
import 'package:unit2/utils/urls.dart';
class ImagePickerScreen extends StatefulWidget {
@override
_ImagePickerScreenState createState() => _ImagePickerScreenState();
}
class _ImagePickerScreenState extends State<ImagePickerScreen> {
File? _image;
final String imagePath = '/data/user/0/com.app.rpass/cache/182.png';
Future<void> _pickImage() async {
final pickedFile =
await ImagePicker().pickImage(source: ImageSource.gallery);
setState(() {
if (pickedFile != null) {
_image = File(pickedFile.path);
} else {
print('No image selected.');
}
});
}
Future<Response> _postBuildingDetails(Map<String, dynamic> details) async {
String xClientKey = "unitK3CQaXiWlPReDsBzmmwBZPd9Re1z";
String xClientKeySecret = "unitcYqAN7GGalyz";
// Construct the headers for the request
Map<String, String> headers = {
'Content-Type': 'multipart/form-data',
'X-Client-Key': xClientKey,
'X-Client-Secret': xClientKeySecret,
};
// Create a MultipartRequest
var request = MultipartRequest(
'POST',
Uri.parse(
'https://${Url.instance.host()}/api/rptass_app/bldgappr_sketch/'),
);
// Add the headers to the request
request.headers.addAll(headers);
// Add JSON data as a field
// Add individual fields to the request
details.forEach((key, value) {
request.fields[key] = value.toString();
});
var file = File(imagePath);
// Add the floor sketch image file, if it exists
var fileName = basename(file.path);
request.files.add(
await MultipartFile.fromPath(
'floor_sketch', // Field name in the API
file.path,
filename: fileName,
),
);
// Send the request and get the response
var streamedResponse = await request.send();
return await Response.fromStream(streamedResponse);
}
Future<void> _uploadImage() async {
// Create a map with the required fields
var file = File(imagePath);
Map<String, dynamic> detailsMap = {
"bldgappr_details_id": 182, // int8 NOT NULL
"date_created": DateTime.now().toIso8601String(), // timestamptz NULL
"floor_sketch": file.path, // text NULL
"gen_code": "5TH", // varchar(20) NOT NULL
};
try {
Response response = await _postBuildingDetails(detailsMap);
print(response.body);
if (response.statusCode == 201) {
print('Upload successful');
} else {
print('Upload failed with status: ${response.statusCode}');
}
} catch (e) {
print('Error: $e');
}
}
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text('Pick and Upload Image'),
),
body: SingleChildScrollView(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
_image == null ? Text('No image selected.') : Image.file(_image!),
SizedBox(height: 20),
ElevatedButton(
onPressed: _pickImage,
child: Text('Pick Image'),
// return "192.168.10.221:3004";
),
SizedBox(height: 20),
ElevatedButton(
onPressed: _uploadImage,
child: Text('Upload Image'),
),
],
),
),
);
}
}

View File

@ -31,6 +31,7 @@ class LandRefLocationOfflinePage extends StatefulWidget {
class _LandRefLocationOfflinePage extends State<LandRefLocationOfflinePage> {
final DateTime now;
final String formatter;
bool sameOwner = false;
_LandRefLocationOfflinePage()
: now = DateTime.now(),
@ -126,8 +127,8 @@ class _LandRefLocationOfflinePage extends State<LandRefLocationOfflinePage> {
children: <Widget>[
Expanded(
flex: 1,
child: customTextField(
"No. / Street", "", 'street'),
child: customTextField("No. / Street", "",
'street', TextInputType.text),
),
const SizedBox(width: 10.0),
Expanded(
@ -144,49 +145,92 @@ class _LandRefLocationOfflinePage extends State<LandRefLocationOfflinePage> {
fontWeight: FontWeight.bold, fontSize: 18),
textAlign: TextAlign.left),
),
customTextField("Land Owner", "", 'l_owner'),
Column(
mainAxisAlignment: MainAxisAlignment.start,
children: [
Row(
children: [
SizedBox(
width: 50, // Adjust the width as needed
height: 50, // Adjust the height as needed
child: Checkbox(
checkColor: Colors.white,
value: sameOwner,
onChanged: (bool? value) {
setState(() {
sameOwner = value!;
offlineBldgKey.currentState!
.patchValue({
'l_owner': offlineBldgKey.currentState
?.value['fname'] +
' ' +
offlineBldgKey.currentState
?.value['mname'] +
' ' +
offlineBldgKey
.currentState?.value['lname']
});
offlineBldgKey.currentState!
.patchValue({
'l_td_arp': offlineBldgKey
.currentState?.value['arp_td']
});
});
},
),
),
Text('Same building owner')
],
),
// Other widgets in the column
],
),
customTextField(
"Land Owner", "", 'l_owner', TextInputType.text),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField(
"OCT/TCT/CLOA No.", "", 'oct_tct_cloa'),
child: customTextField("OCT/TCT/CLOA No.", "",
'oct_tct_cloa', TextInputType.phone),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField("Survey No.", "",
'survey_no', TextInputType.phone))
]),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField("Lot No.", "", 'lot_no',
TextInputType.streetAddress),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField("Blk No.", "",
'blk_no', TextInputType.phone))
]),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField("TD / ARP No.", "",
'l_td_arp', TextInputType.phone),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField(
"Survey No.", "", 'survey_no'))
]),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField("Lot No.", "", 'lot_no'),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child:
customTextField("Blk No.", "", 'blk_no'))
]),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField(
"TD / ARP No.", "", 'l_td_arp'),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField("Area", "", 'area'))
"Area", "", 'area', TextInputType.phone))
]),
const SizedBox(
height: 50,
@ -298,7 +342,7 @@ class _LandRefLocationOfflinePage extends State<LandRefLocationOfflinePage> {
?.value['municipality']
.cityDescription ??
"",
province: "Agusan Del Norte",
province: "AGUSAN DEL NORTE",
genCode: "5th"));
context.read<LandrefLocationBloc>().add(AddLandRef(
@ -324,7 +368,7 @@ class _LandRefLocationOfflinePage extends State<LandRefLocationOfflinePage> {
?.value['l_td_arp'] ??
"",
area:
offlineBldgKey.currentState?.value['area'] ?? "",
offlineBldgKey.currentState?.value['area'] ?? "0",
surveyNo: offlineBldgKey.currentState?.value['survey_no'] ?? "",
blkNo: offlineBldgKey.currentState?.value['blk_no'] ?? "",
genCode: '5th'));

View File

@ -589,7 +589,7 @@ class _PropertyAppraisalOfflinePage
...state.bldgAndStructure
.map((dataRow) {
return DataRow(cells: [
DataCell(Text(dataRow.actualUse!)),
DataCell(Text(dataRow.structType!)),
DataCell(Text("")),
DataCell(Text(
NumberFormat.currency(

File diff suppressed because it is too large Load Diff

View File

@ -23,6 +23,7 @@ class _PropertyInfoPage extends State<PropertyInfoOfflinePage> {
final transaction_codes = ['New', 'Revision'];
final DateTime now;
final String formatter;
bool isOptional = false;
_PropertyInfoPage()
: now = DateTime.now(),
@ -52,12 +53,14 @@ class _PropertyInfoPage extends State<PropertyInfoOfflinePage> {
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField("ARP No. / TD No.", "", 'arp_td')),
child: customTextField("ARP No. / TD No.", "", 'arp_td',
TextInputType.phone)),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField("Pin", "", 'pin')),
child: customTextField(
"Pin", "", 'pin', TextInputType.phone)),
],
),
Row(
@ -65,65 +68,111 @@ class _PropertyInfoPage extends State<PropertyInfoOfflinePage> {
children: <Widget>[
Expanded(
flex: 1,
child: customTextField("First Name", "", 'fname'),
child: customTextField(
"First Name", "", 'fname', TextInputType.text),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField("Middle Name", "", 'mname'),
child: customTextField(
"Middle Name", "", 'mname', TextInputType.text),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField("Last Name", "", 'lname'),
child: customTextField(
"Last Name", "", 'lname', TextInputType.text),
)
]),
customDatTimePicker("Birthday", "", "bday"),
customTextField("Address", "", 'address'),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
customTextField("Address", "", 'address', TextInputType.text),
Column(
mainAxisAlignment: MainAxisAlignment.start,
children: [
Row(
children: [
SizedBox(
width: 50, // Adjust the width as needed
height: 50, // Adjust the height as needed
child: Checkbox(
checkColor: Colors.white,
value: isOptional,
onChanged: (bool? value) {
setState(() {
isOptional = value!;
});
},
),
),
Text('Show optional information')
],
),
// Other widgets in the column
],
),
Visibility(
visible: isOptional,
child: Column(
children: <Widget>[
Expanded(
flex: 1,
child: customTextField("Tel No.", "", 'tel_no'),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField(
"Tel No.", "", 'tel_no', TextInputType.phone),
),
const SizedBox(width: 10.0),
Expanded(
flex: 1,
child: customTextField(
"TIN", "", 'tin', TextInputType.phone),
),
],
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField("TIN", "", 'tin'))
]),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField(
"Administrator / Benificial User", "", 'benificiary'),
const SizedBox(height: 10.0),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField(
"Administrator / Beneficial User",
"",
'benificiary',
TextInputType.text,
),
),
const SizedBox(width: 10.0),
Expanded(
flex: 1,
child: customTextField("TIN", "", 'benificiary_tin',
TextInputType.phone),
),
],
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField("TIN", "", 'benificiary_tin'))
]),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child:
customTextField("Address", "", 'benificiary_address'),
const SizedBox(height: 10.0),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField("Address", "",
'benificiary_address', TextInputType.text),
),
const SizedBox(width: 10.0),
Expanded(
flex: 1,
child: customTextField("Tel No.", "",
'benificiary_telno', TextInputType.phone),
),
],
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child:
customTextField("Tel No.", "", 'benificiary_telno'))
]),
],
),
),
const SizedBox(height: 25),
CustomButton(
icon: const Icon(Icons.chevron_right, color: Colors.white),
@ -136,37 +185,39 @@ class _PropertyInfoPage extends State<PropertyInfoOfflinePage> {
transCode: offlineBldgKey
.currentState!.value['transaction_code']
?.toString() ??
'',
' ',
tdn: offlineBldgKey.currentState!.value['arp_td'] ??
'',
pin:
offlineBldgKey.currentState!.value['pin'] ?? '',
fname: offlineBldgKey.currentState!.value['fname'] ??
'',
mname: offlineBldgKey.currentState!.value['mname'] ??
'',
lname: offlineBldgKey.currentState!.value['lname'] ??
'',
' ',
pin: offlineBldgKey.currentState!.value['pin'] ??
' ',
fname:
offlineBldgKey.currentState!.value['fname'] ??
' ',
mname:
offlineBldgKey.currentState!.value['mname'] ??
' ',
lname:
offlineBldgKey.currentState!.value['lname'] ??
' ',
bday: offlineBldgKey.currentState!.value['bday']
.toString() ??
'',
' ',
address:
offlineBldgKey.currentState!.value['address'] ??
'',
telno: offlineBldgKey.currentState!.value['tel_no'] ??
'',
tin:
offlineBldgKey.currentState!.value['tin'] ?? '',
adminUser:
offlineBldgKey.currentState!.value['benificiary'] ?? '',
adminAddress: offlineBldgKey.currentState!.value['benificiary_address'] ?? '',
adminTin: offlineBldgKey.currentState!.value['benificiary_tin'] ?? '',
adminTelno: offlineBldgKey.currentState!.value['benificiary_telno'] ?? '',
' ',
telno:
offlineBldgKey.currentState!.value['tel_no'] ??
' ',
tin: offlineBldgKey.currentState!.value['tin'] ?? ' ',
adminUser: offlineBldgKey.currentState!.value['benificiary'] ?? ' ',
adminAddress: offlineBldgKey.currentState!.value['benificiary_address'] ?? ' ',
adminTin: offlineBldgKey.currentState!.value['benificiary_tin'] ?? ' ',
adminTelno: offlineBldgKey.currentState!.value['benificiary_telno'] ?? ' ',
faasType: "BUILDING",
assessedById: widget.offlineProfile.id.toString(),
assessedByName: widget.offlineProfile.firstName!,
dateCreated: formatter,
dateModified: '',
dateModified: ' ',
genCode: '5th'),
);
widget.handleButtonPress();

View File

@ -0,0 +1,213 @@
import 'dart:developer';
import 'dart:typed_data';
import 'package:flutter/material.dart';
import 'package:flutter_svg/svg.dart';
import 'package:signature/signature.dart';
import 'package:unit2/screens/offline/passo/building/add/utils.dart';
class SignatureDraw extends StatefulWidget {
const SignatureDraw({super.key});
@override
State<SignatureDraw> createState() => _HomeState();
}
class _HomeState extends State<SignatureDraw> {
// initialize the signature controller
final SignatureController _controller = SignatureController(
penStrokeWidth: 1,
penColor: Colors.red,
exportBackgroundColor: Colors.transparent,
exportPenColor: Colors.black,
onDrawStart: () => log('onDrawStart called!'),
onDrawEnd: () => log('onDrawEnd called!'),
);
@override
void initState() {
super.initState();
_controller
..addListener(() => log('Value changed'))
..onDrawEnd = () => setState(
() {
// setState for build to update value of "empty label" in gui
},
);
}
@override
void dispose() {
// IMPORTANT to dispose of the controller
_controller.dispose();
super.dispose();
}
Future<void> exportImage(BuildContext context) async {
if (_controller.isEmpty) {
ScaffoldMessenger.of(context).showSnackBar(
const SnackBar(
key: Key('snackbarPNG'),
content: Text('No content'),
),
);
return;
}
final Uint8List? data =
await _controller.toPngBytes(height: 1000, width: 1000);
if (data == null) {
return;
}
if (!mounted) return;
await push(
context,
Scaffold(
appBar: AppBar(
title: const Text('PNG Image'),
),
body: Center(
child: Container(
color: Colors.grey[300],
child: Image.memory(data),
),
),
),
);
}
Future<void> exportSVG(BuildContext context) async {
if (_controller.isEmpty) {
ScaffoldMessenger.of(context).showSnackBar(
const SnackBar(
key: Key('snackbarSVG'),
content: Text('No content'),
),
);
return;
}
final SvgPicture data = _controller.toSVG()!;
if (!mounted) return;
await push(
context,
Scaffold(
appBar: AppBar(
title: const Text('SVG Image'),
),
body: Center(
child: Container(
color: Colors.grey[300],
child: data,
),
),
),
);
}
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: const Text('Signature Demo'),
),
body: ListView(
children: <Widget>[
const SizedBox(
height: 300,
child: Center(
child: Text('Big container to test scrolling issues'),
),
),
//SIGNATURE CANVAS
Padding(
padding: const EdgeInsets.all(16.0),
child: Signature(
key: const Key('signature'),
controller: _controller,
height: 300,
backgroundColor: Colors.grey[300]!,
),
),
Text(_controller.isEmpty
? "Signature pad is empty"
: "Signature pad is not empty"),
const SizedBox(
height: 300,
child: Center(
child: Text('Big container to test scrolling issues'),
),
),
],
),
bottomNavigationBar: BottomAppBar(
child: Container(
decoration: const BoxDecoration(color: Colors.black),
child: Row(
mainAxisAlignment: MainAxisAlignment.spaceAround,
mainAxisSize: MainAxisSize.max,
children: <Widget>[
//SHOW EXPORTED IMAGE IN NEW ROUTE
IconButton(
key: const Key('exportPNG'),
icon: const Icon(Icons.image),
color: Colors.blue,
onPressed: () => exportImage(context),
tooltip: 'Export Image',
),
IconButton(
key: const Key('exportSVG'),
icon: const Icon(Icons.share),
color: Colors.blue,
onPressed: () => exportSVG(context),
tooltip: 'Export SVG',
),
IconButton(
icon: const Icon(Icons.undo),
color: Colors.blue,
onPressed: () {
setState(() => _controller.undo());
},
tooltip: 'Undo',
),
IconButton(
icon: const Icon(Icons.redo),
color: Colors.blue,
onPressed: () {
setState(() => _controller.redo());
},
tooltip: 'Redo',
),
//CLEAR CANVAS
IconButton(
key: const Key('clear'),
icon: const Icon(Icons.clear),
color: Colors.blue,
onPressed: () {
setState(() => _controller.clear());
},
tooltip: 'Clear',
),
// STOP Edit
IconButton(
key: const Key('stop'),
icon: Icon(
_controller.disabled ? Icons.pause : Icons.play_arrow,
),
color: Colors.blue,
onPressed: () {
setState(() => _controller.disabled = !_controller.disabled);
},
tooltip: _controller.disabled ? 'Pause' : 'Play',
),
],
),
),
),
);
}
}

View File

@ -29,6 +29,22 @@ class StructuralMaterialsOfflinePage extends StatefulWidget {
final List<String> flooring;
final List<String> walls;
final bool foundationOthers;
final bool columOthers;
final bool beamsOthers;
final bool tfOthers;
final bool roofOthers;
final bool flooringOthers;
final bool wpOthers;
final Function(bool) updateFoundationOthers;
final Function(bool) updateColumOthers;
final Function(bool) updateBeamsOthers;
final Function(bool) updateTfOthers;
final Function(bool) updateRoofOthers;
final Function(bool) updateFlooringOthers;
final Function(bool) updateWpOthers;
final Function(List<String>) updateFoundation;
final Function(List<String>) updateColumn;
final Function(List<String>) updateBeam;
@ -55,6 +71,20 @@ class StructuralMaterialsOfflinePage extends StatefulWidget {
required this.updateRoof,
required this.updateFlooring,
required this.updateWalls,
required this.updateFoundationOthers,
required this.updateColumOthers,
required this.updateBeamsOthers,
required this.updateTfOthers,
required this.updateRoofOthers,
required this.updateFlooringOthers,
required this.updateWpOthers,
required this.foundationOthers,
required this.columOthers,
required this.beamsOthers,
required this.tfOthers,
required this.roofOthers,
required this.flooringOthers,
required this.wpOthers,
// Repeat for other update methods...
});
@ -72,13 +102,6 @@ class _StructuralMaterialsOfflinePage
// List<String> roof = [];
// List<String> flooring = [];
// List<String> walls = [];
bool foundationOthers = false;
bool columOthers = false;
bool beamsOthers = false;
bool tfOthers = false;
bool roofOthers = false;
bool flooringOthers = false;
bool wpOthers = false;
List<MaterialOption> columnOptions = [
MaterialOption('steel', 'Steel'),
@ -114,10 +137,10 @@ class _StructuralMaterialsOfflinePage
const Text('Others'),
Checkbox(
checkColor: Colors.white,
value: foundationOthers,
value: widget.foundationOthers,
onChanged: (bool? value) {
structuralState(() {
foundationOthers = value!;
widget.updateFoundationOthers(value!);
});
},
)
@ -127,9 +150,9 @@ class _StructuralMaterialsOfflinePage
Padding(
padding: const EdgeInsets.only(top: 10.0, bottom: 10.0),
child: Visibility(
visible: foundationOthers,
child: customTextField(
"Enter other foundation", "", "other_foundation"),
visible: widget.foundationOthers,
child: customTextField("Enter other foundation", "",
"other_foundation", TextInputType.text),
replacement: DropDownMultiSelect(
selected_values_style: TextStyle(color: Colors.black),
onChanged: (List<String> x) {
@ -151,10 +174,10 @@ class _StructuralMaterialsOfflinePage
const Text('Others'),
Checkbox(
checkColor: Colors.white,
value: columOthers,
value: widget.columOthers,
onChanged: (bool? value) {
structuralState(() {
columOthers = value!;
widget.updateColumOthers(value!);
});
},
)
@ -164,9 +187,9 @@ class _StructuralMaterialsOfflinePage
Padding(
padding: const EdgeInsets.only(top: 10.0, bottom: 10.0),
child: Visibility(
visible: columOthers,
child:
customTextField("Enter other columns", "", "other_column"),
visible: widget.columOthers,
child: customTextField("Enter other columns", "",
"other_column", TextInputType.text),
replacement: DropDownMultiSelect(
selected_values_style: TextStyle(color: Colors.black),
onChanged: (List<String> x) {
@ -188,10 +211,10 @@ class _StructuralMaterialsOfflinePage
const Text('Others'),
Checkbox(
checkColor: Colors.white,
value: beamsOthers,
value: widget.beamsOthers,
onChanged: (bool? value) {
structuralState(() {
beamsOthers = value!;
widget.updateBeamsOthers(value!);
});
},
)
@ -201,8 +224,9 @@ class _StructuralMaterialsOfflinePage
Padding(
padding: const EdgeInsets.only(top: 10.0, bottom: 10.0),
child: Visibility(
visible: beamsOthers,
child: customTextField("Enter other beam/s", "", "other_beam"),
visible: widget.beamsOthers,
child: customTextField(
"Enter other beam/s", "", "other_beam", TextInputType.text),
replacement: DropDownMultiSelect(
selected_values_style: TextStyle(color: Colors.black),
onChanged: (List<String> x) {
@ -224,10 +248,10 @@ class _StructuralMaterialsOfflinePage
const Text('Others'),
Checkbox(
checkColor: Colors.white,
value: tfOthers,
value: widget.tfOthers,
onChanged: (bool? value) {
structuralState(() {
tfOthers = value!;
widget.updateTfOthers(value!);
});
},
)
@ -237,9 +261,9 @@ class _StructuralMaterialsOfflinePage
Padding(
padding: const EdgeInsets.only(top: 10.0, bottom: 10.0),
child: Visibility(
visible: tfOthers,
child: customTextField(
"Enter other truss framing/s", "", "other_tf"),
visible: widget.tfOthers,
child: customTextField("Enter other truss framing/s", "",
"other_tf", TextInputType.text),
replacement: DropDownMultiSelect(
selected_values_style: TextStyle(color: Colors.black),
onChanged: (List<String> x) {
@ -261,10 +285,10 @@ class _StructuralMaterialsOfflinePage
const Text('Others'),
Checkbox(
checkColor: Colors.white,
value: roofOthers,
value: widget.roofOthers,
onChanged: (bool? value) {
structuralState(() {
roofOthers = value!;
widget.updateRoofOthers(value!);
});
},
)
@ -274,8 +298,9 @@ class _StructuralMaterialsOfflinePage
Padding(
padding: const EdgeInsets.only(top: 10.0, bottom: 10.0),
child: Visibility(
visible: roofOthers,
child: customTextField("Enter other roof/s", "", "other_roof"),
visible: widget.roofOthers,
child: customTextField(
"Enter other roof/s", "", "other_roof", TextInputType.text),
replacement: DropDownMultiSelect(
selected_values_style: TextStyle(color: Colors.black),
onChanged: (List<String> x) {
@ -306,10 +331,10 @@ class _StructuralMaterialsOfflinePage
const Text('Others'),
Checkbox(
checkColor: Colors.white,
value: flooringOthers,
value: widget.flooringOthers,
onChanged: (bool? value) {
structuralState(() {
flooringOthers = value!;
widget.updateFlooringOthers(value!);
});
},
)
@ -319,9 +344,9 @@ class _StructuralMaterialsOfflinePage
Padding(
padding: const EdgeInsets.only(top: 10.0, bottom: 10.0),
child: Visibility(
visible: flooringOthers,
child: customTextField(
"Enter other flooring/s", "", "other_flooring"),
visible: widget.flooringOthers,
child: customTextField("Enter other flooring/s", "",
"other_flooring", TextInputType.text),
replacement: DropDownMultiSelect(
selected_values_style: TextStyle(color: Colors.black),
onChanged: (List<String> x) {
@ -349,10 +374,10 @@ class _StructuralMaterialsOfflinePage
const Text('Others'),
Checkbox(
checkColor: Colors.white,
value: wpOthers,
value: widget.wpOthers,
onChanged: (bool? value) {
structuralState(() {
wpOthers = value!;
widget.updateWpOthers(value!);
});
},
)
@ -362,9 +387,9 @@ class _StructuralMaterialsOfflinePage
Padding(
padding: const EdgeInsets.only(top: 10.0, bottom: 10.0),
child: Visibility(
visible: wpOthers,
child: customTextField(
"Enter other walls & partition/s", "", "other_wp"),
visible: widget.wpOthers,
child: customTextField("Enter other walls & partition/s", "",
"other_wp", TextInputType.text),
replacement: DropDownMultiSelect(
selected_values_style: TextStyle(color: Colors.black),
onChanged: (List<String> x) {
@ -405,60 +430,63 @@ class _StructuralMaterialsOfflinePage
{
final tempID = await SharedPreferences.getInstance();
context
.read<StructuralMaterialOfflineBloc>()
.add(
AddStructuralMaterial(
id: 1,
bldgapprDetailsId: tempID.getInt('tempid')!,
assessedById: '',
assessedByName: '',
dateCreated: '',
dateModified: '',
foundation: foundationOthers
? [
offlineBldgKey.currentState!
.value['other_foundation']
]
: widget.foundation,
columns: columOthers
? [
offlineBldgKey.currentState!
.value['other_column']
]
: widget.column,
beams: beamsOthers
context.read<StructuralMaterialOfflineBloc>().add(
AddStructuralMaterial(
id: 1,
bldgapprDetailsId: tempID.getInt('tempid')!,
assessedById: '',
assessedByName: '',
dateCreated: '',
dateModified: '',
foundation: widget.foundationOthers
? [
offlineBldgKey.currentState!
.value['other_foundation']
]
: widget.foundation,
columns: widget
.columOthers
? [
offlineBldgKey
.currentState!.value['other_column']
]
: widget.column,
beams:
widget
.beamsOthers
? [
offlineBldgKey
.currentState!.value['other_beam']
]
: widget.beam,
trussFraming: tfOthers
? [
offlineBldgKey
.currentState!.value['other_tf']
]
: widget.trussFraming,
roof: roofOthers
trussFraming: widget.tfOthers
? [
offlineBldgKey
.currentState!.value['other_tf']
]
: widget.trussFraming,
roof:
widget.roofOthers
? [
offlineBldgKey
.currentState!.value['other_roof']
]
: widget.roof,
flooring: flooringOthers
flooring:
widget.flooringOthers
? [
offlineBldgKey.currentState!
.value['other_flooring']
]
: widget.flooring,
walls: wpOthers
? [
offlineBldgKey
.currentState!.value['other_wp']
]
: widget.walls,
others: const ["Others"],
genCode: '5th'));
walls: widget.wpOthers
? [
offlineBldgKey
.currentState!.value['other_wp']
]
: widget.walls,
others: const ["Others"],
genCode: '5th'));
widget.NextBtn();
}
;

View File

@ -0,0 +1,12 @@
import 'package:flutter/material.dart';
/// Pushes a widget to a new route.
Future push(context, widget) {
return Navigator.of(context).push(
MaterialPageRoute(
builder: (BuildContext context) {
return widget;
},
),
);
}

View File

@ -31,7 +31,7 @@ class _AddExtraItemsEditOffline extends State<AddExtraItemsEditOffline> {
bool isSecondHand = false;
TextEditingController textEditingController = TextEditingController();
double _unitBase = 0;
int _areaValue = 0;
double _areaValue = 0;
double _depValue = 0;
double _unitValue = 0;
double _marketValue = 0;
@ -106,115 +106,145 @@ class _AddExtraItemsEditOffline extends State<AddExtraItemsEditOffline> {
Container(
margin: const EdgeInsets.only(
left: 0, top: 10, right: 0, bottom: 0),
child: FormBuilderDropdown(
name: 'extra_item',
autofocus: false,
decoration:
normalTextFieldStyle("Additional Item", ""),
items: widget.options
.map((e) => DropdownMenuItem(
value: e,
child: Text(e.componentName!),
))
.toList(),
onChanged: (value) {
if (value!.minBaseUnitvalPercent != '0.00') {
setState(() {
_unitValue = double.parse(
value.minBaseUnitvalPercent!);
_className = value.componentName!;
_classId = value.id!;
_withoutBUCC =
value.withoutBucc == '1' ? true : false;
});
formKey.currentState!.patchValue(
{'unitValue': value.minBaseUnitvalPercent});
}
if (value.maxBaseUnitvalPercent != '0.00') {
setState(() {
_unitValue = double.parse(
value.maxBaseUnitvalPercent!);
_className = value.componentName!;
_classId = value.id!;
_withoutBUCC =
value.withoutBucc == '1' ? true : false;
});
formKey.currentState!.patchValue(
{'unitValue': value.maxBaseUnitvalPercent});
}
if (value.minUnitvalSqrmtr != '0.00') {
setState(() {
_unitValue =
double.parse(value.minUnitvalSqrmtr!);
_className = value.componentName!;
_classId = value.id!;
_withoutBUCC =
value.withoutBucc == '1' ? true : false;
});
formKey.currentState!.patchValue(
{'unitValue': value.minUnitvalSqrmtr});
}
if (value.maxUnitvalSqrmtr != '0.00') {
setState(() {
_unitValue =
double.parse(value.maxUnitvalSqrmtr!);
_className = value.componentName!;
_classId = value.id!;
_withoutBUCC =
value.withoutBucc == '1' ? true : false;
});
formKey.currentState!.patchValue(
{'unitValue': value.maxUnitvalSqrmtr});
}
if (value.minAddBaseunitval != '0.00') {
setState(() {
_unitValue =
double.parse(value.minAddBaseunitval!);
_className = value.componentName!;
_classId = value.id!;
_withoutBUCC =
value.withoutBucc == '1' ? true : false;
});
formKey.currentState!.patchValue(
{'unitValue': value.minAddBaseunitval});
}
if (value.maxAddBaseunitval != '0.00') {
setState(() {
_unitValue =
double.parse(value.maxAddBaseunitval!);
_className = value.componentName!;
_classId = value.id!;
_withoutBUCC =
value.withoutBucc == '1' ? true : false;
});
formKey.currentState!.patchValue(
{'unitValue': value.maxAddBaseunitval});
}
if (value.minDeductBaserate != '0.00') {
setState(() {
_unitValue =
double.parse(value.minDeductBaserate!);
_className = value.componentName!;
_classId = value.id!;
_withoutBUCC =
value.withoutBucc == '1' ? true : false;
});
formKey.currentState!.patchValue(
{'unitValue': value.minDeductBaserate});
}
if (value.maxDeductBaserate != '0.00') {
setState(() {
_unitValue =
double.parse(value.maxDeductBaserate!);
_className = value.componentName!;
_classId = value.id!;
_withoutBUCC =
value.withoutBucc == '1' ? true : false;
});
formKey.currentState!.patchValue(
{'unitValue': value.maxDeductBaserate});
}
},
child: SizedBox(
height: 45,
width: 300,
child: FormBuilderDropdown(
name: 'extra_item',
autofocus: false,
decoration:
normalTextFieldStyle("Additional Item", ""),
items: widget.options
.map((e) => DropdownMenuItem(
value: e,
child: Text(e.componentName!),
))
.toList(),
onChanged: (value) {
if (value!.minBaseUnitvalPercent != '0.00') {
setState(() {
_unitValue = double.parse(
value.minBaseUnitvalPercent!);
_className = value.componentName!;
_classId = value.id!;
_withoutBUCC =
value.withoutBucc == 1 ? true : false;
});
formKey.currentState!.patchValue({
'unitValue': value.minBaseUnitvalPercent
});
formKey.currentState!.patchValue({
'buccValue': (double.parse(
value.minBaseUnitvalPercent!) *
100)
.toString()
});
}
if (value.maxBaseUnitvalPercent != '0.00') {
setState(() {
_unitValue = double.parse(
value.maxBaseUnitvalPercent!);
_className = value.componentName!;
_classId = value.id!;
_withoutBUCC =
value.withoutBucc == 1 ? true : false;
});
formKey.currentState!.patchValue({
'unitValue': value.maxBaseUnitvalPercent
});
formKey.currentState!.patchValue({
'buccValue': (double.parse(
value.maxBaseUnitvalPercent!) *
100)
.toString()
});
}
if (value.minUnitvalSqrmtr != '0.00') {
setState(() {
_unitValue =
double.parse(value.minUnitvalSqrmtr!);
_className = value.componentName!;
_classId = value.id!;
_withoutBUCC =
value.withoutBucc == 1 ? true : false;
});
formKey.currentState!.patchValue(
{'unitValue': value.minUnitvalSqrmtr});
formKey.currentState!
.patchValue({'buccValue': '100'});
}
if (value.maxUnitvalSqrmtr != '0.00') {
setState(() {
_unitValue =
double.parse(value.maxUnitvalSqrmtr!);
_className = value.componentName!;
_classId = value.id!;
_withoutBUCC =
value.withoutBucc == 1 ? true : false;
});
formKey.currentState!.patchValue(
{'unitValue': value.maxUnitvalSqrmtr});
formKey.currentState!
.patchValue({'buccValue': '100'});
}
if (value.minAddBaseunitval != '0.00') {
setState(() {
_unitValue =
double.parse(value.minAddBaseunitval!);
_className = value.componentName!;
_classId = value.id!;
_withoutBUCC =
value.withoutBucc == 1 ? true : false;
});
formKey.currentState!.patchValue(
{'unitValue': value.minAddBaseunitval});
formKey.currentState!
.patchValue({'buccValue': '100'});
}
if (value.maxAddBaseunitval != '0.00') {
setState(() {
_unitValue =
double.parse(value.maxAddBaseunitval!);
_className = value.componentName!;
_classId = value.id!;
_withoutBUCC =
value.withoutBucc == 1 ? true : false;
});
formKey.currentState!.patchValue(
{'unitValue': value.maxAddBaseunitval});
formKey.currentState!
.patchValue({'buccValue': '100'});
}
if (value.minDeductBaserate != '0.00') {
setState(() {
_unitValue =
double.parse(value.minDeductBaserate!);
_className = value.componentName!;
_classId = value.id!;
_withoutBUCC =
value.withoutBucc == 1 ? true : false;
});
formKey.currentState!.patchValue(
{'unitValue': value.minDeductBaserate});
formKey.currentState!
.patchValue({'buccValue': '100'});
}
if (value.maxDeductBaserate != '0.00') {
setState(() {
_unitValue =
double.parse(value.maxDeductBaserate!);
_className = value.componentName!;
_classId = value.id!;
_withoutBUCC =
value.withoutBucc == 1 ? true : false;
});
formKey.currentState!.patchValue(
{'unitValue': value.maxDeductBaserate});
formKey.currentState!
.patchValue({'buccValue': '100'});
}
},
),
),
),
const SizedBox(height: 10),
@ -228,15 +258,11 @@ class _AddExtraItemsEditOffline extends State<AddExtraItemsEditOffline> {
suggestions: widget.unit
.map((UnitConstruct unit) =>
SearchFieldListItem(
unit.bldgType! +
' - ' +
unit.building,
'${unit.bldgType} - ${unit.building}',
item: unit,
child: ListTile(
title: Text(
unit.bldgType +
' - ' +
unit.building!.toUpperCase(),
'${unit.bldgType} - ${unit.building!.toUpperCase()}',
overflow: TextOverflow.ellipsis,
),
)))
@ -255,41 +281,26 @@ class _AddExtraItemsEditOffline extends State<AddExtraItemsEditOffline> {
suggestionState: Suggestion.expand,
onSuggestionTap: (unit) {
setState(() {
_unitBase =
double.parse(unit.item!.unitValue);
_structureType = unit.item!.bldgType +
' - ' +
unit.item!.building;
if (_withoutBUCC) {
_unitBase = _unitValue;
_structureType =
'${unit.item!.bldgType} - ${unit.item!.building}';
formKey.currentState!
.patchValue({'buccValue': '100'});
} else {
_unitBase =
double.parse(unit.item!.unitValue);
_structureType =
'${unit.item!.bldgType} - ${unit.item!.building}';
formKey.currentState!.patchValue(
{'unitValue': unit.item!.unitValue});
}
});
focus.unfocus();
},
),
),
),
// const SizedBox(height: 10),
// Container(
// margin: const EdgeInsets.only(
// left: 0, top: 10, right: 0, bottom: 0),
// child: FormBuilderDropdown(
// name: 'struc_type',
// autofocus: false,
// decoration:
// normalTextFieldStyle("Structure Type", ""),
// items: widget.unit
// .map((e) => DropdownMenuItem(
// value: e,
// child:
// Text(e.bldgType + " - " + e.building),
// ))
// .toList(),
// onChanged: (val) {
// setState(() {
// _unitBase = double.parse(val!.unitValue);
// _structureType = val.bldgType;
// });
// },
// ),
// ),
const SizedBox(height: 10),
Row(
children: [
@ -299,75 +310,60 @@ class _AddExtraItemsEditOffline extends State<AddExtraItemsEditOffline> {
name: 'unitValue',
decoration:
normalTextFieldStyle("Unit Value", ""),
keyboardType: TextInputType.phone,
validator: FormBuilderValidators.compose([]),
),
),
const SizedBox(width: 10),
Expanded(
flex: 1,
child: FormBuilderTextField(
name: 'buccValue',
decoration: normalTextFieldStyle("BUCC", ""),
keyboardType: TextInputType.phone,
validator: FormBuilderValidators.compose([]),
onChanged: (value) {
// setState(() {
// _areaValue = double.parse(value!);
// });
},
),
),
const SizedBox(
height: 40,
width: 40,
child: Center(
child: Text(
'%',
style: TextStyle(
fontSize: 18,
fontWeight: FontWeight.bold),
),
),
)
],
),
SizedBox(
height: 10,
),
Row(
children: [
Expanded(
flex: 1,
child: FormBuilderTextField(
name: 'areaValue',
decoration: normalTextFieldStyle("Area", ""),
keyboardType: TextInputType.phone,
validator: FormBuilderValidators.compose([]),
onChanged: (value) {
setState(() {
_areaValue = int.parse(value!);
_areaValue = double.parse(value!);
});
},
),
),
],
),
// const SizedBox(height: 10),
// FormBuilderTextField(
// name: 'depRate',
// decoration:
// normalTextFieldStyle("Depreciation Rate", ""),
// validator: FormBuilderValidators.compose([]),
// onChanged: (value) {
// setState(() {
// _depValue = double.parse(value!);
// });
// },
// ),
// const SizedBox(height: 10),
// FormBuilderTextField(
// name: 'marketValue',
// decoration: normalTextFieldStyle(
// NumberFormat.currency(
// locale: 'en-PH', symbol: "")
// .format(_totalMarketValue(_unitValue,
// _unitBase, _areaValue, _depValue)),
// ""),
// validator: FormBuilderValidators.compose([]),
// onChanged: (value) {
// setState(() {
// _marketValue = double.parse(value!);
// });
// },
// ),
// const SizedBox(height: 10),
// Text('Amount of Depreciation'),
// const SizedBox(height: 5),
// Container(
// height: 45.0,
// width: double.infinity,
// decoration: BoxDecoration(
// color: Colors.white,
// border: Border.all(
// color: Colors.grey,
// width: 1.0,
// ),
// borderRadius: BorderRadius.circular(5.0),
// ),
// child: Align(
// alignment: Alignment.center,
// child: Text(NumberFormat.currency(
// locale: 'en-PH', symbol: "")
// .format(_amountofDepreciation(_unitValue,
// _unitBase, _areaValue, _depValue)))),
// ),
Visibility(
visible: !_withoutBUCC,
child: Column(
@ -451,6 +447,7 @@ class _AddExtraItemsEditOffline extends State<AddExtraItemsEditOffline> {
validator:
FormBuilderValidators.compose(
[]),
keyboardType: TextInputType.phone,
onChanged: (value) {
// Check if the value is not null before parsing to double
if (value != null &&
@ -486,7 +483,6 @@ class _AddExtraItemsEditOffline extends State<AddExtraItemsEditOffline> {
],
),
),
const SizedBox(height: 10),
Text('Market Value'),
const SizedBox(height: 5),
@ -539,8 +535,8 @@ class _AddExtraItemsEditOffline extends State<AddExtraItemsEditOffline> {
className: _className,
structType: _structureType,
unitValue: _withoutBUCC == true
? 0
: _unitValue,
? 100
: _unitValue * 100,
baseUnitValue: _unitBase.toString(),
area: _areaValue,
marketValue:
@ -574,7 +570,7 @@ class _AddExtraItemsEditOffline extends State<AddExtraItemsEditOffline> {
genCode: "5th"));
},
style: ElevatedButton.styleFrom(
primary: Colors.black,
backgroundColor: Colors.black,
),
child: const Text("Submit"),
),
@ -593,7 +589,7 @@ class _AddExtraItemsEditOffline extends State<AddExtraItemsEditOffline> {
.add(LoadAdditionalItems());
},
style: ElevatedButton.styleFrom(
primary: Colors.black,
backgroundColor: Colors.black,
),
child: const Text("Cancel"),
),

View File

@ -371,6 +371,7 @@ class _AddExtraItemsOffline extends State<AddExtraItemsOffline> {
validator:
FormBuilderValidators.compose(
[]),
keyboardType: TextInputType.phone,
),
),
const SizedBox(width: 10),
@ -380,6 +381,7 @@ class _AddExtraItemsOffline extends State<AddExtraItemsOffline> {
name: 'areaValue',
decoration: normalTextFieldStyle(
"Area", ""),
keyboardType: TextInputType.phone,
validator:
FormBuilderValidators.compose(
[]),
@ -537,6 +539,8 @@ class _AddExtraItemsOffline extends State<AddExtraItemsOffline> {
normalTextFieldStyle(
"Unit Value",
""),
keyboardType:
TextInputType.phone,
validator:
FormBuilderValidators
.compose([]),
@ -688,7 +692,7 @@ class _AddExtraItemsOffline extends State<AddExtraItemsOffline> {
}
},
style: ElevatedButton.styleFrom(
primary: Colors.black,
backgroundColor: Colors.black,
),
child: const Text("Submit"),
),
@ -709,7 +713,7 @@ class _AddExtraItemsOffline extends State<AddExtraItemsOffline> {
const LoadAdditionalItems());
},
style: ElevatedButton.styleFrom(
primary: Colors.black,
backgroundColor: Colors.black,
),
child: const Text("Cancel"),
),

View File

@ -67,141 +67,137 @@ class _AdditionalItemEditPageOffline
if (state is AdditionalItemsLoaded) {
return Column(
children: [
Container(
height: 500,
child: Expanded(
child: SingleChildScrollView(
child: Padding(
padding: const EdgeInsets.all(15.0),
child: Column(
children: [
Container(
margin: const EdgeInsets.only(
left: 0, top: 20, right: 0, bottom: 10),
child: const Text('ADDITIONAL ITEMS',
style: TextStyle(
fontWeight: FontWeight.bold,
fontSize: 18),
textAlign: TextAlign.left),
),
Align(
alignment: Alignment.topRight,
child: ElevatedButton(
style: ElevatedButton.styleFrom(
backgroundColor: Colors.red,
),
onPressed: () {
context
.read<AdditionalItemsOfflineBloc>()
.add(ShowAdditionalItems());
},
child: const Row(
mainAxisSize: MainAxisSize.min,
children: [
Text('ADD ITEM'), // <-- Text
SizedBox(
width: 5,
),
Icon(
// <-- Icon
Icons.add,
size: 24.0,
),
],
),
Expanded(
child: SingleChildScrollView(
child: Padding(
padding: const EdgeInsets.all(15.0),
child: Column(
children: [
Container(
margin: const EdgeInsets.only(
left: 0, top: 20, right: 0, bottom: 10),
child: const Text('ADDITIONAL ITEMS',
style: TextStyle(
fontWeight: FontWeight.bold,
fontSize: 18),
textAlign: TextAlign.left),
),
Align(
alignment: Alignment.topRight,
child: ElevatedButton(
style: ElevatedButton.styleFrom(
backgroundColor: Colors.red,
),
),
SingleChildScrollView(
scrollDirection: Axis.horizontal,
child: DataTable(
// ignore: prefer_const_literals_to_create_immutables
columns: [
const DataColumn(
label: Text('Items'),
onPressed: () {
context
.read<AdditionalItemsOfflineBloc>()
.add(ShowAdditionalItems());
},
child: const Row(
mainAxisSize: MainAxisSize.min,
children: [
Text('ADD ITEM'), // <-- Text
SizedBox(
width: 5,
),
const DataColumn(
label: Text('Unit Value'),
Icon(
// <-- Icon
Icons.add,
size: 24.0,
),
const DataColumn(
label: Text('% of BUCC'),
),
const DataColumn(
label: Text('Market Value'),
),
const DataColumn(
label: Text('Action'),
)
],
rows: state.addItem.map((dataRow) {
return DataRow(
cells: [
DataCell(Text(dataRow.className)),
DataCell(Text(NumberFormat.currency(
locale: 'en-PH',
symbol: "",
).format(double.parse(
dataRow.baseUnitValue)))),
DataCell(
Text(dataRow.unitValue.toString())),
DataCell(Text(NumberFormat.currency(
locale: 'en-PH',
symbol: "",
).format(double.parse(
dataRow.adjustedMarketVal)))),
DataCell(Row(
children: [
InkWell(
child: Container(
height: 30,
width: 30,
decoration: const BoxDecoration(
shape: BoxShape.circle,
color: Colors.red,
),
child: const Icon(
Icons.delete,
color: Colors.white,
size: 20.0,
),
),
onTap: () {
confirmAlertWithCancel(
context,
() =>
deleteItem(dataRow.id!),
() => null,
'Delete Item?',
"Are you sure you want to delete this item?");
},
),
const SizedBox(
width: 10,
),
InkWell(
child: Container(
height: 30,
width: 30,
decoration: const BoxDecoration(
shape: BoxShape.circle,
color: Colors.red,
),
child: const Icon(
Icons.edit,
color: Colors.white,
size: 20.0,
),
),
onTap: () {},
),
],
))
],
);
}).toList(),
),
),
],
),
),
SingleChildScrollView(
scrollDirection: Axis.horizontal,
child: DataTable(
// ignore: prefer_const_literals_to_create_immutables
columns: [
const DataColumn(
label: Text('Items'),
),
const DataColumn(
label: Text('Unit Value'),
),
const DataColumn(
label: Text('% of BUCC'),
),
const DataColumn(
label: Text('Market Value'),
),
const DataColumn(
label: Text('Action'),
)
],
rows: state.addItem.map((dataRow) {
return DataRow(
cells: [
DataCell(Text(dataRow.className)),
DataCell(Text(NumberFormat.currency(
locale: 'en-PH',
symbol: "",
).format(double.parse(
dataRow.baseUnitValue)))),
DataCell(
Text(dataRow.unitValue.toString())),
DataCell(Text(NumberFormat.currency(
locale: 'en-PH',
symbol: "",
).format(double.parse(
dataRow.adjustedMarketVal)))),
DataCell(Row(
children: [
InkWell(
child: Container(
height: 30,
width: 30,
decoration: const BoxDecoration(
shape: BoxShape.circle,
color: Colors.red,
),
child: const Icon(
Icons.delete,
color: Colors.white,
size: 20.0,
),
),
onTap: () {
confirmAlertWithCancel(
context,
() => deleteItem(dataRow.id!),
() => null,
'Delete Item?',
"Are you sure you want to delete this item?");
},
),
const SizedBox(
width: 10,
),
InkWell(
child: Container(
height: 30,
width: 30,
decoration: const BoxDecoration(
shape: BoxShape.circle,
color: Colors.red,
),
child: const Icon(
Icons.edit,
color: Colors.white,
size: 20.0,
),
),
onTap: () {},
),
],
))
],
);
}).toList(),
),
),
],
),
),
),

View File

@ -9,13 +9,16 @@ import 'package:unit2/bloc/offline/offline_passo/admin/unit_construction/unit_co
import 'package:unit2/model/offline/offline_profile.dart';
import 'package:unit2/screens/offline/passo/building/edit/additional_items_edit.dart';
import 'package:unit2/screens/offline/passo/building/edit/building_and_structure.dart';
import 'package:unit2/screens/offline/passo/building/edit/flutter_painter_edit.dart';
import 'package:unit2/screens/offline/passo/building/edit/general_description_edit.dart';
import 'package:unit2/screens/offline/passo/building/edit/landref_location_edit.dart';
import 'package:unit2/screens/offline/passo/building/edit/property_appraisal_edit.dart';
import 'package:unit2/screens/offline/passo/building/edit/property_assessment_edit.dart';
import 'package:unit2/screens/offline/passo/building/edit/property_owner_info_edit.dart';
import 'package:unit2/screens/offline/passo/building/edit/structural_materials_edit.dart';
import 'package:unit2/utils/alerts.dart';
import '../../../../../bloc/offline/offline_passo/building/structural_materials_offline.dart/structural_material_offline_bloc.dart';
import '../../../../../model/passo/property_info.dart';
import '../../../../../theme-data.dart/colors.dart';
@ -26,13 +29,15 @@ class EditBuildingOffline extends StatefulWidget {
final PropertyInfo faas;
final String title;
final OfflineProfile offlineProfile;
final Function loadBldg;
const EditBuildingOffline(
{super.key,
required this.title,
required this.index,
required this.faas,
required this.offlineProfile});
required this.offlineProfile,
required this.loadBldg});
@override
_EditBuildingOffline createState() => _EditBuildingOffline();
}
@ -41,7 +46,7 @@ class _EditBuildingOffline extends State<EditBuildingOffline> {
// THE FOLLOWING TWO VARIABLES ARE REQUIRED TO CONTROL THE STEPPER.
int activeStep = 0; // Initial step set to 5.
int upperBound = 7; // upperBound MUST BE total number of icons minus 1.
int upperBound = 8; // upperBound MUST BE total number of icons minus 1.
void PrevBtn() {
setState(() {
@ -56,73 +61,158 @@ class _EditBuildingOffline extends State<EditBuildingOffline> {
}
void onSAveAll() {
return Navigator.of(context).pop();
Navigator.of(context).pop();
widget.loadBldg();
}
List<String> foundation = [];
List<String> column = [];
List<String> beam = [];
List<String> trussFraming = [];
List<String> roof = [];
List<String> flooring = [];
List<String> walls = [];
void updateFoundation(List<String> updatedList) {
setState(() {
foundation = updatedList;
});
}
void updateColumn(List<String> updatedList) {
setState(() {
column = updatedList;
});
}
void updateBeam(List<String> updatedList) {
setState(() {
beam = updatedList;
});
}
void updateTrussFraming(List<String> updatedList) {
setState(() {
trussFraming = updatedList;
});
}
void updateRoof(List<String> updatedList) {
setState(() {
roof = updatedList;
});
}
void updateFlooring(List<String> updatedList) {
setState(() {
flooring = updatedList;
});
}
void updateWalls(List<String> updatedList) {
setState(() {
walls = updatedList;
});
}
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
centerTitle: true,
backgroundColor: primary,
title: const Text('Building FAAS Edit'),
),
body: ProgressHUD(
padding: const EdgeInsets.all(24),
backgroundColor: Colors.black87,
indicatorWidget: const SpinKitFadingCircle(color: Colors.white),
child: BlocConsumer<UnitConstructionAdminBloc,
UnitConstructionAdminState>(
listener: (context, state) {
// TODO: implement listener
},
builder: (context, state) {
if (state is UnitConstructLoaded) {
final unit = state.unit;
return BlocConsumer<ClassComponentsAdminBloc,
ClassComponentsAdminState>(
listener: (context, state) {
// TODO: implement listener
},
builder: (context, state) {
if (state is ClassComponentsAdminLoaded) {
return Column(
children: [
NumberStepper(
numbers: const [1, 2, 3, 4, 5, 6, 7, 8],
activeStepColor: primary,
numberStyle: const TextStyle(color: Colors.white),
lineColor: primary,
// activeStep property set to activeStep variable defined above.
activeStep: activeStep,
activeStepBorderColor: Colors.white,
activeStepBorderWidth: 1,
// This ensures step-tapping updates the activeStep.
onStepReached: (index) {
setState(() {
activeStep = index;
});
},
),
Expanded(
child: StatefulBuilder(builder:
(BuildContext context, StateSetter setState) {
return Container(
child: content(
PrevBtn, NextBtn, unit, state.classes),
return WillPopScope(
onWillPop: () async {
confirmAlertWithCancel(
context,
onSAveAll,
() => null,
'Cancel Editing?',
"Unsaved edited data will not be saved, are you sure you want to exit?"); // Action to perform on back pressed
return false;
},
child: Scaffold(
appBar: AppBar(
centerTitle: true,
backgroundColor: primary,
title: const Text('Building FAAS Edit'),
),
body: ProgressHUD(
padding: const EdgeInsets.all(24),
backgroundColor: Colors.black87,
indicatorWidget: const SpinKitFadingCircle(color: Colors.white),
child: BlocConsumer<StructuralMaterialOfflineBloc,
StructuralMaterialOfflineState>(
listener: (context, state) {
// TODO: implement listener
},
builder: (context, state) {
if (state is SpecificStructuralMaterialLoaded) {
return BlocConsumer<UnitConstructionAdminBloc,
UnitConstructionAdminState>(
listener: (context, state) {
// TODO: implement listener
},
builder: (context, state) {
if (state is UnitConstructLoaded) {
final unit = state.unit;
return BlocConsumer<ClassComponentsAdminBloc,
ClassComponentsAdminState>(
listener: (context, state) {
// TODO: implement listener
},
builder: (context, state) {
if (state is ClassComponentsAdminLoaded) {
return Column(
children: [
NumberStepper(
numbers: const [
1,
2,
3,
4,
5,
6,
7,
8,
9
],
activeStepColor: primary,
numberStyle:
const TextStyle(color: Colors.white),
lineColor: primary,
// activeStep property set to activeStep variable defined above.
activeStep: activeStep,
activeStepBorderColor: Colors.white,
activeStepBorderWidth: 1,
// This ensures step-tapping updates the activeStep.
onStepReached: (index) {
setState(() {
activeStep = index;
});
},
),
Expanded(
child: StatefulBuilder(builder:
(BuildContext context,
StateSetter setState) {
return Container(
child: content(PrevBtn, NextBtn, unit,
state.classes),
);
}),
),
],
);
}),
),
],
);
}
return Container();
},
);
}
return Container();
},
)));
}
return Container();
},
);
}
return Container();
},
);
}
return Container();
},
))),
);
}
// Returns the header text based on the activeStep.
@ -132,7 +222,7 @@ class _EditBuildingOffline extends State<EditBuildingOffline> {
return PropertyOwnerInfoEditOffline(
widget.index,
widget.faas,
'EDit',
'Edit',
PrevBtn,
NextBtn,
);
@ -143,24 +233,28 @@ class _EditBuildingOffline extends State<EditBuildingOffline> {
case 2:
return GeneralDescriptionEditOffline(widget.faas.id!, NextBtn, PrevBtn);
case 3:
case 4:
return BuildingAndStructureOfflinePage(
PrevBtn, NextBtn, widget.offlineProfile);
case 4:
case 3:
return FlutterDrawEdit(widget.faas.id!);
case 5:
return StructuralMaterialsPageEditOffline(
widget.faas.id!, NextBtn, PrevBtn);
case 5:
case 6:
return AdditionalItemEditPageOffline(
unit, classes, widget.faas.id!, NextBtn, PrevBtn);
case 6:
case 7:
return PropertyAppraisalEditPageOffline(
widget.faas.id!, NextBtn, PrevBtn);
case 7:
return PropertyAssessmentEditOfflinePage(widget.faas.id!, onSAveAll);
case 8:
return PropertyAssessmentEditOfflinePage(
widget.faas.id!, onSAveAll, widget.offlineProfile);
default:
return Container();

View File

@ -0,0 +1,814 @@
import 'dart:async';
import 'dart:io';
import 'dart:ui';
import 'package:http/http.dart'; // Removed 'as http'
import 'package:path/path.dart'; // For basename function
import 'dart:convert';
import 'package:flutter/foundation.dart';
import 'package:flutter/material.dart';
import 'package:flutter_painter_v2/flutter_painter.dart';
import 'package:flutter_painter_v2/flutter_painter_extensions.dart';
import 'package:flutter_painter_v2/flutter_painter_pure.dart';
import 'package:path_provider/path_provider.dart';
import 'dart:ui' as ui;
import 'package:phosphor_flutter/phosphor_flutter.dart';
import 'package:shared_preferences/shared_preferences.dart';
import 'package:unit2/model/passo/floor_sketch.dart';
import 'package:unit2/utils/urls.dart';
import '../../../../../sevices/offline/offline_passo/admin/sql_services/sql_services.dart';
class FlutterDrawEdit extends StatefulWidget {
final int tempId;
FlutterDrawEdit(this.tempId);
@override
_FlutterPainterExampleState createState() => _FlutterPainterExampleState();
}
class _FlutterPainterExampleState extends State<FlutterDrawEdit> {
static const Color red = Color.fromARGB(255, 0, 0, 0);
FocusNode textFocusNode = FocusNode();
late PainterController controller;
ui.Image? backgroundImage;
Paint shapePaint = Paint()
..strokeWidth = 5
..color = Colors.black
..style = PaintingStyle.stroke
..strokeCap = StrokeCap.round;
File? _image;
final String imagePath = '/data/user/0/com.app.rpass/cache/182.png';
static const List<String> imageLinks = [
"https://i.imgur.com/btoI5OX.png",
"https://i.imgur.com/EXTQFt7.png",
"https://i.imgur.com/EDNjJYL.png",
"https://i.imgur.com/uQKD6NL.png",
"https://i.imgur.com/cMqVRbl.png",
"https://i.imgur.com/1cJBAfI.png",
"https://i.imgur.com/eNYfHKL.png",
"https://i.imgur.com/c4Ag5yt.png",
"https://i.imgur.com/GhpCJuf.png",
"https://i.imgur.com/XVMeluF.png",
"https://i.imgur.com/mt2yO6Z.png",
"https://i.imgur.com/rw9XP1X.png",
"https://i.imgur.com/pD7foZ8.png",
"https://i.imgur.com/13Y3vp2.png",
"https://i.imgur.com/ojv3yw1.png",
"https://i.imgur.com/f8ZNJJ7.png",
"https://i.imgur.com/BiYkHzw.png",
"https://i.imgur.com/snJOcEz.png",
"https://i.imgur.com/b61cnhi.png",
"https://i.imgur.com/FkDFzYe.png",
"https://i.imgur.com/P310x7d.png",
"https://i.imgur.com/5AHZpua.png",
"https://i.imgur.com/tmvJY4r.png",
"https://i.imgur.com/PdVfGkV.png",
"https://i.imgur.com/1PRzwBf.png",
"https://i.imgur.com/VeeMfBS.png",
];
@override
void initState() {
super.initState();
controller = PainterController(
settings: PainterSettings(
text: TextSettings(
focusNode: textFocusNode,
textStyle: const TextStyle(
fontWeight: FontWeight.bold, color: red, fontSize: 18),
),
freeStyle: const FreeStyleSettings(
color: red,
strokeWidth: 5,
),
shape: ShapeSettings(
paint: shapePaint,
),
scale: const ScaleSettings(
enabled: true,
minScale: 1,
maxScale: 5,
)));
// Listen to focus events of the text field
textFocusNode.addListener(onFocus);
// Initialize background
initBackground();
}
/// Fetches image from an [ImageProvider] (in this example, [NetworkImage])
/// to use it as a background
void initBackground() async {
final prefs = await SharedPreferences.getInstance();
final floorSketchSaved = prefs.getBool('floorSketchSaved') ?? false;
print(floorSketchSaved);
ui.Image image;
final String imagePath =
'/data/user/0/com.app.rpass/cache/${widget.tempId}.png';
image = await _loadImageFromPath(imagePath);
setState(() {
backgroundImage = image;
controller.background = image.backgroundDrawable;
});
}
/// Updates UI when the focus changes
void onFocus() {
setState(() {});
}
Future<ui.Image> _loadImageFromPath(String imagePath) async {
final file = File(imagePath);
final bytes = await file.readAsBytes();
final Completer<ui.Image> completer = Completer();
ui.decodeImageFromList(bytes, (ui.Image img) {
completer.complete(img);
});
return completer.future;
}
Future<void> deleteImage(BuildContext context) async {
final prefs = await SharedPreferences.getInstance();
final String imagePath =
'/data/user/0/com.app.rpass/cache/${widget.tempId}.png';
final file = File(imagePath);
if (await file.exists()) {
await file.delete();
ScaffoldMessenger.of(context).showSnackBar(
SnackBar(content: Text('Image deleted successfully')),
);
final image = await const AssetImage('assets/pngs/white_bg.png').image;
setState(() {
backgroundImage = image;
controller.background = image.backgroundDrawable;
});
} else {
ScaffoldMessenger.of(context).showSnackBar(
SnackBar(content: Text('Image does not exist')),
);
}
}
Widget buildDefault(BuildContext context) {
return Scaffold(
appBar: PreferredSize(
preferredSize: const Size(double.infinity, kToolbarHeight),
// Listen to the controller and update the UI when it updates.
child: ValueListenableBuilder<PainterControllerValue>(
valueListenable: controller,
builder: (context, _, child) {
return AppBar(
title: child,
automaticallyImplyLeading: false, // Disable the back button
actions: [
// Delete the selected drawable
IconButton(
icon: const Icon(
PhosphorIcons.trash,
),
onPressed: controller.selectedObjectDrawable == null
? null
: removeSelectedDrawable,
),
// Delete the selected drawable
IconButton(
icon: const Icon(
Icons.flip,
),
onPressed: controller.selectedObjectDrawable != null &&
controller.selectedObjectDrawable is ImageDrawable
? flipSelectedImageDrawable
: null,
),
// Redo action
IconButton(
icon: const Icon(
PhosphorIcons.arrowClockwise,
),
onPressed: controller.canRedo ? redo : null,
),
// Undo action
IconButton(
icon: const Icon(
PhosphorIcons.arrowCounterClockwise,
),
onPressed: controller.canUndo ? undo : null,
),
],
);
}),
),
// Generate image
floatingActionButton: Stack(
children: <Widget>[
Align(
alignment: Alignment.bottomRight,
child: FloatingActionButton(
heroTag: 'btn1',
child: const Icon(
PhosphorIcons.imageFill,
),
onPressed: () => renderAndDisplayImage(context),
),
),
Align(
alignment: Alignment.bottomRight,
child: Padding(
padding: const EdgeInsets.only(bottom: 60.0),
child: FloatingActionButton(
heroTag: 'btn2',
child: const Icon(
Icons.delete,
),
onPressed: () => deleteImage(context),
),
),
),
// Add more FloatingActionButton widgets here if needed
],
),
body: Stack(
children: [
if (backgroundImage != null)
// Enforces constraints
Positioned.fill(
child: Center(
child: AspectRatio(
aspectRatio:
backgroundImage!.width / backgroundImage!.height,
child: FlutterPainter(
controller: controller,
),
),
),
),
Positioned(
bottom: 0,
right: 0,
left: 0,
child: ValueListenableBuilder(
valueListenable: controller,
builder: (context, _, __) => Row(
mainAxisAlignment: MainAxisAlignment.center,
children: [
Flexible(
child: Container(
constraints: const BoxConstraints(
maxWidth: 400,
),
padding: const EdgeInsets.symmetric(horizontal: 15),
decoration: const BoxDecoration(
borderRadius:
BorderRadius.vertical(top: Radius.circular(20)),
color: Colors.white54,
),
child: Column(
mainAxisSize: MainAxisSize.min,
children: [
if (controller.freeStyleMode !=
FreeStyleMode.none) ...[
const Divider(),
const Text("Free Style Settings"),
// Control free style stroke width
Row(
children: [
const Expanded(
flex: 1, child: Text("Stroke Width")),
Expanded(
flex: 3,
child: Slider.adaptive(
min: 2,
max: 25,
value: controller.freeStyleStrokeWidth,
onChanged: setFreeStyleStrokeWidth),
),
],
),
if (controller.freeStyleMode ==
FreeStyleMode.draw)
Row(
children: [
const Expanded(
flex: 1, child: Text("Color")),
// Control free style color hue
Expanded(
flex: 3,
child: Slider.adaptive(
min: 0,
max: 359.99,
value: HSVColor.fromColor(
controller.freeStyleColor)
.hue,
activeColor:
controller.freeStyleColor,
onChanged: setFreeStyleColor),
),
],
),
],
if (textFocusNode.hasFocus) ...[
const Divider(),
const Text("Text settings"),
// Control text font size
Row(
children: [
const Expanded(
flex: 1, child: Text("Font Size")),
Expanded(
flex: 3,
child: Slider.adaptive(
min: 8,
max: 96,
value:
controller.textStyle.fontSize ?? 14,
onChanged: setTextFontSize),
),
],
),
// Control text color hue
Row(
children: [
const Expanded(flex: 1, child: Text("Color")),
Expanded(
flex: 3,
child: Slider.adaptive(
min: 0,
max: 359.99,
value: HSVColor.fromColor(
controller.textStyle.color ??
red)
.hue,
activeColor: controller.textStyle.color,
onChanged: setTextColor),
),
],
),
],
if (controller.shapeFactory != null) ...[
const Divider(),
const Text("Shape Settings"),
// Control text color hue
Row(
children: [
const Expanded(
flex: 1, child: Text("Stroke Width")),
Expanded(
flex: 3,
child: Slider.adaptive(
min: 2,
max: 25,
value: controller
.shapePaint?.strokeWidth ??
shapePaint.strokeWidth,
onChanged: (value) =>
setShapeFactoryPaint(
(controller.shapePaint ??
shapePaint)
.copyWith(
strokeWidth: value,
))),
),
],
),
// Control shape color hue
Row(
children: [
const Expanded(flex: 1, child: Text("Color")),
Expanded(
flex: 3,
child: Slider.adaptive(
min: 0,
max: 359.99,
value: HSVColor.fromColor(
(controller.shapePaint ??
shapePaint)
.color)
.hue,
activeColor: (controller.shapePaint ??
shapePaint)
.color,
onChanged: (hue) =>
setShapeFactoryPaint(
(controller.shapePaint ??
shapePaint)
.copyWith(
color: HSVColor.fromAHSV(
1, hue, 1, 1)
.toColor(),
))),
),
],
),
Row(
children: [
const Expanded(
flex: 1, child: Text("Fill shape")),
Expanded(
flex: 3,
child: Center(
child: Switch(
value: (controller.shapePaint ??
shapePaint)
.style ==
PaintingStyle.fill,
onChanged: (value) =>
setShapeFactoryPaint(
(controller.shapePaint ??
shapePaint)
.copyWith(
style: value
? PaintingStyle.fill
: PaintingStyle.stroke,
))),
),
),
],
),
]
],
),
),
),
],
),
),
),
],
),
bottomNavigationBar: ValueListenableBuilder(
valueListenable: controller,
builder: (context, _, __) => Row(
mainAxisAlignment: MainAxisAlignment.spaceAround,
children: [
// Free-style eraser
IconButton(
icon: Icon(
PhosphorIcons.eraser,
color: controller.freeStyleMode == FreeStyleMode.erase
? Theme.of(context).primaryColor
: null,
),
onPressed: toggleFreeStyleErase,
),
// Free-style drawing
IconButton(
icon: Icon(
PhosphorIcons.scribbleLoop,
color: controller.freeStyleMode == FreeStyleMode.draw
? Theme.of(context).primaryColor
: null,
),
onPressed: toggleFreeStyleDraw,
),
// Add text
IconButton(
icon: Icon(
PhosphorIcons.textT,
color: textFocusNode.hasFocus
? Theme.of(context).primaryColor
: null,
),
onPressed: addText,
),
// Add sticker image
IconButton(
icon: const Icon(
PhosphorIcons.sticker,
),
onPressed: () => addSticker(context),
),
// Add shapes
if (controller.shapeFactory == null)
PopupMenuButton<ShapeFactory?>(
tooltip: "Add shape",
itemBuilder: (context) => <ShapeFactory, String>{
LineFactory(): "Line",
ArrowFactory(): "Arrow",
DoubleArrowFactory(): "Double Arrow",
RectangleFactory(): "Rectangle",
OvalFactory(): "Oval",
}
.entries
.map((e) => PopupMenuItem(
value: e.key,
child: Row(
mainAxisAlignment: MainAxisAlignment.start,
children: [
Icon(
getShapeIcon(e.key),
color: Colors.black,
),
Text(" ${e.value}")
],
)))
.toList(),
onSelected: selectShape,
child: Padding(
padding: const EdgeInsets.all(8.0),
child: Icon(
getShapeIcon(controller.shapeFactory),
color: controller.shapeFactory != null
? Theme.of(context).primaryColor
: null,
),
),
)
else
IconButton(
icon: Icon(
getShapeIcon(controller.shapeFactory),
color: Theme.of(context).primaryColor,
),
onPressed: () => selectShape(null),
),
],
),
));
}
@override
Widget build(BuildContext context) {
return buildDefault(context);
}
static IconData getShapeIcon(ShapeFactory? shapeFactory) {
if (shapeFactory is LineFactory) return PhosphorIcons.lineSegment;
if (shapeFactory is ArrowFactory) return PhosphorIcons.arrowUpRight;
if (shapeFactory is DoubleArrowFactory) {
return PhosphorIcons.arrowsHorizontal;
}
if (shapeFactory is RectangleFactory) return PhosphorIcons.rectangle;
if (shapeFactory is OvalFactory) return PhosphorIcons.circle;
return PhosphorIcons.polygon;
}
void undo() {
controller.undo();
}
void redo() {
controller.redo();
}
void toggleFreeStyleDraw() {
controller.freeStyleMode = controller.freeStyleMode != FreeStyleMode.draw
? FreeStyleMode.draw
: FreeStyleMode.none;
}
void toggleFreeStyleErase() {
controller.freeStyleMode = controller.freeStyleMode != FreeStyleMode.erase
? FreeStyleMode.erase
: FreeStyleMode.none;
}
void addText() {
if (controller.freeStyleMode != FreeStyleMode.none) {
controller.freeStyleMode = FreeStyleMode.none;
}
controller.addText();
}
void addSticker(BuildContext context) async {
final imageLink = await showDialog<String>(
context: context,
builder: (context) => const SelectStickerImageDialog(
imagesLinks: imageLinks,
));
if (imageLink == null) return;
controller.addImage(
await NetworkImage(imageLink).image, const Size(100, 100));
}
void setFreeStyleStrokeWidth(double value) {
controller.freeStyleStrokeWidth = value;
}
void setFreeStyleColor(double hue) {
controller.freeStyleColor = HSVColor.fromAHSV(1, hue, 1, 1).toColor();
}
void setTextFontSize(double size) {
// Set state is just to update the current UI, the [FlutterPainter] UI updates without it
setState(() {
controller.textSettings = controller.textSettings.copyWith(
textStyle:
controller.textSettings.textStyle.copyWith(fontSize: size));
});
}
void setShapeFactoryPaint(Paint paint) {
// Set state is just to update the current UI, the [FlutterPainter] UI updates without it
setState(() {
controller.shapePaint = paint;
});
}
void setTextColor(double hue) {
controller.textStyle = controller.textStyle
.copyWith(color: HSVColor.fromAHSV(1, hue, 1, 1).toColor());
}
void selectShape(ShapeFactory? factory) {
controller.shapeFactory = factory;
}
Future<void> _uploadImage() async {
// Create a map with the required fields
final tempID = await SharedPreferences.getInstance();
final String imagePath =
'/data/user/0/com.app.rpass/cache/${widget.tempId}.png';
await tempID.setBool('floorSketchSaved', true);
var file = File(imagePath);
// Map<String, dynamic> detailsMap = {
// "bldgappr_details_id": 182, // int8 NOT NULL
// "date_created": DateTime.now().toIso8601String(), // timestamptz NULL
// "floor_sketch": file.path, // text NULL
// "gen_code": "5TH", // varchar(20) NOT NULL
// };
var floorSketchs = FloorSketch(
bldgapprDetailsId: widget.tempId,
dateCreated: DateTime.now().toIso8601String(),
floorSketch: file.path,
genCode: "5TH");
try {
// Response response = await _postBuildingDetails(detailsMap);
// print(response.body);
await SQLServices.instance.createFloorSketch(floorSketchs);
// if (response.statusCode == 201) {
// print('Upload successful');
// } else {
// print('Upload failed with status: ${response.statusCode}');
// }
} catch (e) {
if (kDebugMode) {
print('Error: $e');
}
}
}
void renderAndDisplayImage(BuildContext context) async {
if (backgroundImage == null) return;
final backgroundImageSize = Size(
backgroundImage!.width.toDouble(),
backgroundImage!.height.toDouble(),
);
try {
// Render the image
final image = await controller.renderImage(backgroundImageSize);
final byteData = await image.toByteData(format: ui.ImageByteFormat.png);
final imageBytes = byteData!.buffer.asUint8List();
final tempID = await SharedPreferences.getInstance();
// Write the PNG image data to a file
final file =
File('${(await getTemporaryDirectory()).path}/${widget.tempId}.png');
await file.writeAsBytes(imageBytes);
// Show a dialog with the image
// ignore: use_build_context_synchronously
showDialog(
context: context,
builder: (BuildContext context) => AlertDialog(
title: const Text('Rendered Image'),
content: Image.memory(imageBytes),
actions: <Widget>[
TextButton(
child: const Text('SAVE'),
onPressed: () {
_uploadImage();
},
),
TextButton(
child: const Text('Close'),
onPressed: () {
Navigator.of(context).pop();
},
),
],
),
);
// Show a snackbar with the file path
// ignore: use_build_context_synchronously
ScaffoldMessenger.of(context).showSnackBar(
SnackBar(content: Text('Image saved to ${file.path}')),
);
} catch (e) {
// Handle potential errors
// ignore: use_build_context_synchronously
ScaffoldMessenger.of(context).showSnackBar(
SnackBar(content: Text('Error: $e')),
);
}
}
void removeSelectedDrawable() {
final selectedDrawable = controller.selectedObjectDrawable;
if (selectedDrawable != null) controller.removeDrawable(selectedDrawable);
}
void flipSelectedImageDrawable() {
final imageDrawable = controller.selectedObjectDrawable;
if (imageDrawable is! ImageDrawable) return;
controller.replaceDrawable(
imageDrawable, imageDrawable.copyWith(flipped: !imageDrawable.flipped));
}
}
class RenderedImageDialog extends StatelessWidget {
final Future<Uint8List?> imageFuture;
final String imagePath = '/data/user/0/com.app.rpass/cache/182.png';
const RenderedImageDialog({Key? key, required this.imageFuture})
: super(key: key);
@override
Widget build(BuildContext context) {
return AlertDialog(
title: const Text("Rendered Image"),
content: FutureBuilder<Uint8List?>(
future: imageFuture,
builder: (context, snapshot) {
if (snapshot.connectionState != ConnectionState.done) {
return const SizedBox(
height: 50,
child: Center(child: CircularProgressIndicator.adaptive()),
);
}
if (!snapshot.hasData || snapshot.data == null) {
return const SizedBox();
}
return InteractiveViewer(
maxScale: 10, child: Image.memory(snapshot.data!));
},
),
);
}
}
class SelectStickerImageDialog extends StatelessWidget {
final List<String> imagesLinks;
const SelectStickerImageDialog({Key? key, this.imagesLinks = const []})
: super(key: key);
@override
Widget build(BuildContext context) {
return AlertDialog(
title: const Text("Select sticker"),
content: imagesLinks.isEmpty
? const Text("No images")
: FractionallySizedBox(
heightFactor: 0.5,
child: SingleChildScrollView(
child: Wrap(
children: [
for (final imageLink in imagesLinks)
InkWell(
onTap: () => Navigator.pop(context, imageLink),
child: FractionallySizedBox(
widthFactor: 1 / 4,
child: Image.network(imageLink),
),
),
],
),
),
),
actions: [
TextButton(
child: const Text("Cancel"),
onPressed: () => Navigator.pop(context),
)
],
);
}
}

View File

@ -1,8 +1,11 @@
import 'dart:convert';
import 'package:flutter/material.dart';
import 'package:flutter_bloc/flutter_bloc.dart';
import 'package:flutter_form_builder/flutter_form_builder.dart';
import 'package:flutter_progress_hud/flutter_progress_hud.dart';
import 'package:flutter_spinkit/flutter_spinkit.dart';
import 'package:shared_preferences/shared_preferences.dart';
import 'package:unit2/bloc/offline/offline_passo/admin/unit_construction/unit_construction_admin_bloc.dart';
import 'package:unit2/bloc/offline/offline_passo/building/general_description/general_description_bloc.dart';
import 'package:unit2/screens/offline/passo/building/edit/edit_building.dart';
@ -38,356 +41,309 @@ class _GeneralDescriptionEditOffline
@override
Widget build(BuildContext context) {
return Scaffold(
body: Column(
children: [
Expanded(
child: ProgressHUD(
padding: const EdgeInsets.all(24),
backgroundColor: Colors.black87,
indicatorWidget: const SpinKitFadingCircle(color: Colors.white),
child:
BlocConsumer<GeneralDescriptionBloc, GeneralDescriptionState>(
listener: (context, state) async {
// if (state is GenDescLoading) {
// final progress = ProgressHUD.of(context);
// progress!.showWithText("Please wait...");
// }
// if (state is GenDescLoaded) {
// final progress = ProgressHUD.of(context);
// progress?.dismiss();
return BlocConsumer<GeneralDescriptionBloc, GeneralDescriptionState>(
listener: (context, state) async {
// if (state is GenDescLoading) {
// final progress = ProgressHUD.of(context);
// progress!.showWithText("Please wait...");
// }
// if (state is GenDescLoaded) {
// final progress = ProgressHUD.of(context);
// progress?.dismiss();
// final tempID = await SharedPreferences.getInstance();
// await tempID.setInt(
// 'totalValue', int.parse(state.gendesc.totalFloorArea!));
// await tempID.setString(
// 'actualUse', state.gendesc.actualUse!);
// final tempID = await SharedPreferences.getInstance();
// await tempID.setInt(
// 'totalValue', int.parse(state.gendesc.totalFloorArea!));
// await tempID.setString(
// 'actualUse', state.gendesc.actualUse!);
// }
// if (state is GenDescErrorState) {
// final progress = ProgressHUD.of(context);
// progress?.dismiss();
// }
},
builder: (context, state) {
if (state is SpecificGeneralDescriptionLoaded) {
final gendesc = state.gendesc;
return BlocConsumer<UnitConstructionAdminBloc,
UnitConstructionAdminState>(
listener: (context, state) {
// TODO: implement listener
},
builder: (context, state) {
if (state is UnitConstructLoaded) {
return FormBuilder(
key: offlineBldgEditKey,
initialValue: {
'bldg_permit': gendesc.bldgPermit,
'date_issued': gendesc.dateIssued.toString(),
'cct': gendesc.cct.toString(),
'coc_issued':
gendesc.certCompletionIssued.toString(),
'coo_issued':
gendesc.certOccupancyIssued.toString(),
'date_cnstructed': gendesc.dateIssued.toString(),
'date_occupied': gendesc.dateOccupied.toString(),
'bldg_age': gendesc.bldgAge.toString(),
'no_of_storeys': gendesc.noStoreys.toString(),
'area_of_1stFl': gendesc.area1Stfloor,
'area_of_2ndFl': gendesc.area2Ndfloor,
'area_of_3rdFl': gendesc.area3Rdfloor,
'area_of_4thFl': gendesc.area4Thfloor,
'total_area': gendesc.totalFloorArea.toString(),
'actual_use': gendesc.actualUse
},
enabled: true,
onChanged: () {
offlineBldgEditKey.currentState!.save();
debugPrint(offlineBldgEditKey.currentState!.value
.toString());
},
autovalidateMode: AutovalidateMode.disabled,
skipDisabled: true,
child: Expanded(
child: SingleChildScrollView(
scrollDirection: Axis.vertical,
child: Padding(
padding: const EdgeInsets.all(20.0),
child: Column(
children: [
Container(
margin: const EdgeInsets.only(
left: 0,
top: 20,
right: 0,
bottom: 10),
child: const Text('GENERAL DESCRIPTION',
style: TextStyle(
fontWeight: FontWeight.bold,
fontSize: 18),
textAlign: TextAlign.left),
),
Container(
margin: const EdgeInsets.only(
left: 0,
top: 10,
right: 0,
bottom: 0),
child: FormBuilderDropdown(
name: 'bldg_type',
autofocus: false,
decoration: normalTextFieldStyle(
gendesc.bldgKind ??
"Kind of Building",
"Kind of Building"),
items: state.unit
.map((e) => DropdownMenuItem(
value: e,
child: Text(e.bldgType +
'-' +
e.building),
))
.toList(),
),
),
customDropDownField("Actual Use", "",
'actual_use', actual_use),
Row(
mainAxisAlignment:
MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField(
"Bldg. Permit No.",
"",
'bldg_permit'),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customDatTimePicker(
"Certificate of Occupancy Issued ON",
"",
'date_issued'))
]),
customTextField(
"Condominium Certificate of Title (CCT)",
"",
'cct'),
Row(
mainAxisAlignment:
MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customDatTimePicker(
"Certificate of Completion Issued ON",
"",
'coc_issued'),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customDatTimePicker(
"Certificate of Occupancy Issued ON",
"",
'coo_issued'))
]),
Row(
mainAxisAlignment:
MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customDatTimePicker(
"Date Constructed /Completed",
"",
'date_cnstructed'),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customDatTimePicker(
"Date Occupied",
"",
'date_occupied'))
]),
Row(
mainAxisAlignment:
MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField(
"Bldg. Age", "", 'bldg_age'),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField(
"No. of storeys",
"",
'no_of_storeys'))
]),
Row(
mainAxisAlignment:
MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField(
"Area of 1st Floor",
"",
'area_of_1stFl'),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField(
"Area of 2nd Floor",
"",
'area_of_2ndFl'))
]),
Row(
mainAxisAlignment:
MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField(
"Area of 3rd Floor",
"",
'area_of_3rdFl')),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField(
"Area of 4th Floor",
"",
'area_of_4thFl'))
]),
customTextField(
"Total Area", "", 'total_area'),
SizedBox(
height: 50,
),
Row(
mainAxisAlignment:
MainAxisAlignment.spaceEvenly,
children: [
CustomButton(
icon: const Icon(
Icons.chevron_left_rounded,
color: Colors.white),
onPressed: () {
{
widget.PrevBtn();
}
;
},
),
CustomButton(
icon: const Icon(
Icons.chevron_right_rounded,
color: Colors.white),
onPressed: () {
{
offlineBldgEditKey.currentState!
.save();
var gendescData = GeneralDesc(
id: 1,
bldgapprDetailsId:
widget.tempId,
assessedById: "1",
assessedByName: 'hhs',
bldgKind: offlineBldgEditKey
.currentState
?.value['bldg_type']
?.building ??
gendesc.bldgKind,
strucType: offlineBldgEditKey
.currentState
?.value['bldg_type']
?.bldgType ??
gendesc.strucType,
bldgPermit: offlineBldgEditKey.currentState?.value['bldg_permit'] ??
gendesc.bldgPermit,
dateIssued: offlineBldgEditKey.currentState?.value['date_issued'] != null
? offlineBldgEditKey.currentState!.value['date_issued']
.toString()
: gendesc.dateIssued,
cct: offlineBldgEditKey.currentState!.value['cct'] ??
gendesc.cct,
certCompletionIssued:
offlineBldgEditKey
.currentState!
.value['coc_issued']
.toString(),
certOccupancyIssued: offlineBldgEditKey.currentState!.value['coo_issued'].toString(),
dateCompleted: offlineBldgEditKey.currentState!.value['date_cnstructed'].toString(),
dateOccupied: offlineBldgEditKey.currentState!.value['date_occupied'].toString(),
bldgAge: offlineBldgEditKey.currentState?.value['bldg_age']!,
noStoreys: offlineBldgEditKey.currentState?.value['no_of_storeys']!,
area1Stfloor: offlineBldgEditKey.currentState?.value['area_of_1stFl'],
area2Ndfloor: offlineBldgEditKey.currentState?.value['area_of_2ndFl'],
area3Rdfloor: offlineBldgEditKey.currentState?.value['area_of_3rdFl'],
area4Thfloor: offlineBldgEditKey.currentState?.value['area_of_4thFl'],
totalFloorArea: offlineBldgEditKey.currentState?.value['total_area'],
floorSketch: 'null',
actualUse: offlineBldgEditKey.currentState?.value['actual_use'],
unitValue: offlineBldgEditKey.currentState?.value['bldg_type']?.unitValue ?? gendesc.unitValue);
context
.read<
GeneralDescriptionBloc>()
.add(
UpdateGeneralDescription(
id: widget.tempId,
gendesc:
gendescData));
widget.NextBtn();
}
;
},
)
],
)
],
),
),
),
// }
// if (state is GenDescErrorState) {
// final progress = ProgressHUD.of(context);
// progress?.dismiss();
// }
},
builder: (context, state) {
if (state is SpecificGeneralDescriptionLoaded) {
final gendesc = state.gendesc;
return BlocConsumer<UnitConstructionAdminBloc,
UnitConstructionAdminState>(
listener: (context, state) {
// TODO: implement listener
},
builder: (context, state) {
if (state is UnitConstructLoaded) {
return FormBuilder(
key: offlineBldgEditKey,
initialValue: {
'bldg_permit': gendesc.bldgPermit,
'date_issued': gendesc.dateIssued.toString(),
'cct': gendesc.cct.toString(),
'coc_issued': gendesc.certCompletionIssued.toString(),
'coo_issued': gendesc.certOccupancyIssued.toString(),
'date_cnstructed': gendesc.dateIssued.toString(),
'date_occupied': gendesc.dateOccupied.toString(),
'bldg_age': gendesc.bldgAge.toString(),
'no_of_storeys': gendesc.noStoreys.toString(),
'area_of_1stFl': gendesc.area1Stfloor,
'area_of_2ndFl': gendesc.area2Ndfloor,
'area_of_3rdFl': gendesc.area3Rdfloor,
'area_of_4thFl': gendesc.area4Thfloor,
'total_area': gendesc.totalFloorArea.toString(),
'actual_use': gendesc.actualUse
},
enabled: true,
onChanged: () {
offlineBldgEditKey.currentState!.save();
debugPrint(
offlineBldgEditKey.currentState!.value.toString());
},
autovalidateMode: AutovalidateMode.disabled,
skipDisabled: true,
child: SingleChildScrollView(
child: Padding(
padding: const EdgeInsets.all(20.0),
child: Column(
children: [
Container(
margin: const EdgeInsets.only(
left: 0, top: 20, right: 0, bottom: 10),
child: const Text('GENERAL DESCRIPTION',
style: TextStyle(
fontWeight: FontWeight.bold, fontSize: 18),
textAlign: TextAlign.left),
),
Container(
margin: const EdgeInsets.only(
left: 0, top: 10, right: 0, bottom: 0),
child: FormBuilderDropdown(
name: 'bldg_type',
autofocus: false,
decoration: normalTextFieldStyle(
gendesc.bldgKind ?? "Kind of Building",
"Kind of Building"),
items: state.unit
.map((e) => DropdownMenuItem(
value: e,
child:
Text(e.bldgType + '-' + e.building),
))
.toList(),
),
);
}
return Container();
},
);
}
// if (state is GenDescErrorState) {
// return SomethingWentWrong(
// message: onError,
// onpressed: () {
// context.read<GeneralDescriptionBloc>().add(LoadGenDesc(
// id: widget.tempId, gendesc: GeneralDesc()));
// },
// );
// }
return Container();
},
),
),
),
],
),
),
customDropDownField(
"Actual Use", "", 'actual_use', actual_use),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField("Bldg. Permit No.", "",
'bldg_permit', TextInputType.phone),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customDatTimePicker(
"Certificate of Occupancy Issued ON",
"",
'date_issued'))
]),
customTextField(
"Condominium Certificate of Title (CCT)",
"",
'cct',
TextInputType.number),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customDatTimePicker(
"Certificate of Completion Issued ON",
"",
'coc_issued'),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customDatTimePicker(
"Certificate of Occupancy Issued ON",
"",
'coo_issued'))
]),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customDatTimePicker(
"Date Constructed /Completed",
"",
'date_cnstructed'),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customDatTimePicker(
"Date Occupied", "", 'date_occupied'))
]),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField("Bldg. Age", "",
'bldg_age', TextInputType.phone),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField("No. of storeys", "",
'no_of_storeys', TextInputType.phone))
]),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField("Area of 1st Floor",
"", 'area_of_1stFl', TextInputType.phone),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField(
"Area of 2nd Floor",
"",
'area_of_2ndFl',
TextInputType.phone))
]),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField(
"Area of 3rd Floor",
"",
'area_of_3rdFl',
TextInputType.phone)),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField(
"Area of 4th Floor",
"",
'area_of_4thFl',
TextInputType.phone))
]),
customTextField("Total Area", "", 'total_area',
TextInputType.phone),
SizedBox(
height: 50,
),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: [
CustomButton(
icon: const Icon(Icons.chevron_left_rounded,
color: Colors.white),
onPressed: () {
{
widget.PrevBtn();
}
;
},
),
CustomButton(
icon: const Icon(Icons.chevron_right_rounded,
color: Colors.white),
onPressed: () {
{
offlineBldgEditKey.currentState!.save();
var gendescData = GeneralDesc(
id: 1,
bldgapprDetailsId: widget.tempId,
assessedById: "1",
assessedByName: 'hhs',
bldgKind: offlineBldgEditKey
.currentState
?.value['bldg_type']
?.building ??
gendesc.bldgKind,
strucType: offlineBldgEditKey
.currentState
?.value['bldg_type']
?.bldgType ??
gendesc.strucType,
bldgPermit: offlineBldgEditKey
.currentState
?.value['bldg_permit'] ??
gendesc.bldgPermit,
dateIssued: offlineBldgEditKey
.currentState
?.value['date_issued'] !=
null
? offlineBldgEditKey.currentState!.value['date_issued']
.toString()
: gendesc.dateIssued,
cct: offlineBldgEditKey.currentState!.value['cct'] ?? gendesc.cct,
certCompletionIssued: offlineBldgEditKey.currentState!.value['coc_issued'].toString(),
certOccupancyIssued: offlineBldgEditKey.currentState!.value['coo_issued'].toString(),
dateCompleted: offlineBldgEditKey.currentState!.value['date_cnstructed'].toString(),
dateOccupied: offlineBldgEditKey.currentState!.value['date_occupied'].toString(),
bldgAge: offlineBldgEditKey.currentState?.value['bldg_age']!,
noStoreys: offlineBldgEditKey.currentState?.value['no_of_storeys']!,
area1Stfloor: offlineBldgEditKey.currentState?.value['area_of_1stFl'],
area2Ndfloor: offlineBldgEditKey.currentState?.value['area_of_2ndFl'],
area3Rdfloor: offlineBldgEditKey.currentState?.value['area_of_3rdFl'],
area4Thfloor: offlineBldgEditKey.currentState?.value['area_of_4thFl'],
totalFloorArea: offlineBldgEditKey.currentState?.value['total_area'],
floorSketch: 'null',
actualUse: offlineBldgEditKey.currentState?.value['actual_use'],
unitValue: offlineBldgEditKey.currentState?.value['bldg_type']?.unitValue ?? gendesc.unitValue);
context.read<GeneralDescriptionBloc>().add(
UpdateGeneralDescription(
id: widget.tempId,
gendesc: gendescData));
widget.NextBtn();
}
;
},
)
],
)
],
),
),
),
);
}
return Container();
},
);
}
// if (state is GenDescErrorState) {
// return SomethingWentWrong(
// message: onError,
// onpressed: () {
// context.read<GeneralDescriptionBloc>().add(LoadGenDesc(
// id: widget.tempId, gendesc: GeneralDesc()));
// },
// );
// }
return Container();
},
);
}
}

View File

@ -230,7 +230,10 @@ class _BldgLocLandRefEditOffline extends State<BldgLocLandRefEditOffline> {
Expanded(
flex: 1,
child: customTextField(
"No. / Street", "", 'street'),
"No. / Street",
"",
'street',
TextInputType.text),
),
// Expanded(
@ -254,8 +257,8 @@ class _BldgLocLandRefEditOffline extends State<BldgLocLandRefEditOffline> {
fontSize: 18),
textAlign: TextAlign.center),
),
customTextField(
"Land Owner", "", 'l_owner'),
customTextField("Land Owner", "",
'l_owner', TextInputType.text),
Row(
mainAxisAlignment:
MainAxisAlignment.spaceEvenly,
@ -265,7 +268,8 @@ class _BldgLocLandRefEditOffline extends State<BldgLocLandRefEditOffline> {
child: customTextField(
"OCT/TCT/CLOA No.",
"",
'oct_tct_cloa'),
'oct_tct_cloa',
TextInputType.phone),
),
const SizedBox(width: 10.0),
Expanded(
@ -274,7 +278,8 @@ class _BldgLocLandRefEditOffline extends State<BldgLocLandRefEditOffline> {
child: customTextField(
"Survey No.",
"",
'survey_no'))
'survey_no',
TextInputType.phone))
]),
Row(
mainAxisAlignment:
@ -283,14 +288,20 @@ class _BldgLocLandRefEditOffline extends State<BldgLocLandRefEditOffline> {
Expanded(
flex: 1,
child: customTextField(
"Lot No.", "", 'lot_no'),
"Lot No.",
"",
'lot_no',
TextInputType.phone),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField(
"Blk No.", "", 'blk_no'))
"Blk No.",
"",
'blk_no',
TextInputType.phone))
]),
Row(
mainAxisAlignment:
@ -301,14 +312,18 @@ class _BldgLocLandRefEditOffline extends State<BldgLocLandRefEditOffline> {
child: customTextField(
"TD / ARP No.",
"",
'l_td_arp'),
'l_td_arp',
TextInputType.phone),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField(
"Area", "", 'area'))
"Area",
"",
'area',
TextInputType.phone))
]),
SizedBox(
height: 50,

View File

@ -46,198 +46,190 @@ class _PropertyOwnerInfoEditOffline
@override
Widget build(BuildContext context) {
return SingleChildScrollView(
scrollDirection: Axis.vertical,
child: Column(
children: [
Padding(
padding: const EdgeInsets.all(15.0),
child: Expanded(
child: Column(
children: <Widget>[
FormBuilder(
key: offlineBldgEditKey,
initialValue: {
'transaction_code': widget.faas.transCode,
'arp_td': widget.faas.tdn,
'pin': widget.faas.pin,
'fname': widget.faas.fname,
'mname': widget.faas.mname,
'lname': widget.faas.lname,
'bday': widget.faas.bday,
'address': widget.faas.address,
'tel_no': widget.faas.telno,
'tin': widget.faas.tin,
'benificiary': widget.faas.adminUser,
'benificiary_telno': widget.faas.adminTelno,
'benificiary_address': widget.faas.adminAddress,
'benificiary_tin': widget.faas.adminTin,
},
enabled: true,
onChanged: () {
offlineBldgEditKey.currentState!.save();
debugPrint(
offlineBldgEditKey.currentState!.value.toString());
},
autovalidateMode: AutovalidateMode.disabled,
skipDisabled: true,
child: Column(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
child: Padding(
padding: const EdgeInsets.all(15.0),
child: Column(
children: <Widget>[
FormBuilder(
key: offlineBldgEditKey,
initialValue: {
'transaction_code': widget.faas.transCode,
'arp_td': widget.faas.tdn,
'pin': widget.faas.pin,
'fname': widget.faas.fname,
'mname': widget.faas.mname,
'lname': widget.faas.lname,
'bday': widget.faas.bday,
'address': widget.faas.address,
'tel_no': widget.faas.telno,
'tin': widget.faas.tin,
'benificiary': widget.faas.adminUser,
'benificiary_telno': widget.faas.adminTelno,
'benificiary_address': widget.faas.adminAddress,
'benificiary_tin': widget.faas.adminTin,
},
enabled: true,
onChanged: () {
offlineBldgEditKey.currentState!.save();
debugPrint(offlineBldgEditKey.currentState!.value.toString());
},
autovalidateMode: AutovalidateMode.disabled,
skipDisabled: true,
child: Column(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: <Widget>[
Container(
margin: const EdgeInsets.only(
left: 0, top: 20, right: 0, bottom: 10),
child: const Text('PROPERTY OWNER INFO',
style: TextStyle(
fontWeight: FontWeight.bold, fontSize: 18),
textAlign: TextAlign.left),
),
const SizedBox(height: 15),
customDropDownField(
widget.faas.transCode ?? "Transaction Code",
"",
"transaction_code",
transaction_codes),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField("ARP No. / TD No.", "",
'arp_td', TextInputType.phone)),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField(
"Pin", "", 'pin', TextInputType.phone)),
],
),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Container(
margin: const EdgeInsets.only(
left: 0, top: 20, right: 0, bottom: 10),
child: const Text('PROPERTY OWNER INFO',
style: TextStyle(
fontWeight: FontWeight.bold,
fontSize: 18),
textAlign: TextAlign.left),
Expanded(
flex: 1,
child: customTextField("First Name", "", 'fname',
TextInputType.text),
),
const SizedBox(height: 15),
customDropDownField(
widget.faas.transCode ?? "Transaction Code",
"",
"transaction_code",
transaction_codes),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField(
"ARP No. / TD No.", "", 'arp_td')),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField("Pin", "", 'pin')),
],
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField("Middle Name", "", 'mname',
TextInputType.text),
),
Row(
mainAxisAlignment:
MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField(
"First Name", "", 'fname'),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField(
"Middle Name", "", 'mname'),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField(
"Last Name", "", 'lname'),
)
]),
customDatTimePicker("Birthday", "", "bday"),
customTextField("Address", "", 'address'),
Row(
mainAxisAlignment:
MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField(
"Tel No.", "", 'tel_no'),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField("TIN", "", 'tin'))
]),
Row(
mainAxisAlignment:
MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField(
"Administrator / Benificial User",
"",
'benificiary'),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField(
"TIN", "", 'benificiary_tin'))
]),
Row(
mainAxisAlignment:
MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField(
"Address", "", 'benificiary_address'),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField(
"Tel No.", "", 'benificiary_telno'))
]),
const SizedBox(height: 25),
SizedBox(
width: MediaQuery.of(context).size.width,
child: CustomButton(
icon: const Icon(Icons.chevron_right,
color: Colors.white),
onPressed: () {
var property_info = PropertyInfo(
id: widget.faas.id,
transCode: offlineBldgEditKey.currentState
?.value['transaction_code']
.toString() ??
widget.faas.transCode,
assessedById: '1',
assessedByName: 'cyril',
tdn: offlineBldgEditKey
.currentState!.value['arp_td'] ??
widget.faas.tdn,
pin: offlineBldgEditKey.currentState!.value['pin'] ??
widget.faas.pin,
fname: offlineBldgEditKey
.currentState!.value['fname'] ??
widget.faas.fname,
mname: offlineBldgEditKey
.currentState!.value['mname'] ??
widget.faas.mname,
address: offlineBldgEditKey.currentState!.value['address'] ?? widget.faas.address,
telno: offlineBldgEditKey.currentState!.value['tel_no'] ?? widget.faas.telno,
tin: offlineBldgEditKey.currentState!.value['tin'] ?? widget.faas.tin,
adminUser: offlineBldgEditKey.currentState!.value['benificiary'] ?? widget.faas.adminUser,
adminAddress: offlineBldgEditKey.currentState!.value['benificiary_address'] ?? widget.faas.adminAddress,
adminTin: offlineBldgEditKey.currentState!.value['benificiary_tin'] ?? widget.faas.adminTin,
adminTelno: offlineBldgEditKey.currentState!.value['benificiary_telno'] ?? widget.faas.adminTelno,
faasType: "Building");
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField(
"Last Name", "", 'lname', TextInputType.text),
)
]),
customDatTimePicker("Birthday", "", "bday"),
customTextField(
"Address", "", 'address', TextInputType.text),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField(
"Tel No.", "", 'tel_no', TextInputType.phone),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField(
"TIN", "", 'tin', TextInputType.phone))
]),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField(
"Administrator / Benificial User",
"",
'benificiary',
TextInputType.text),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField("TIN", "",
'benificiary_tin', TextInputType.phone))
]),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField("Address", "",
'benificiary_address', TextInputType.text),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField("Tel No.", "",
'benificiary_telno', TextInputType.phone))
]),
const SizedBox(height: 25),
SizedBox(
width: MediaQuery.of(context).size.width,
child: CustomButton(
icon: const Icon(Icons.chevron_right,
color: Colors.white),
onPressed: () {
var property_info = PropertyInfo(
id: widget.faas.id,
transCode: offlineBldgEditKey
.currentState?.value['transaction_code']
.toString() ??
widget.faas.transCode,
assessedById: '1',
assessedByName: 'cyril',
tdn: offlineBldgEditKey.currentState!.value['arp_td'] ??
widget.faas.tdn,
pin: offlineBldgEditKey.currentState!.value['pin'] ??
widget.faas.pin,
fname: offlineBldgEditKey.currentState!.value['fname'] ??
widget.faas.fname,
mname: offlineBldgEditKey.currentState!.value['mname'] ??
widget.faas.mname,
bday: offlineBldgEditKey.currentState!.value['bday']
.toString(),
lname: offlineBldgEditKey.currentState!.value['lname'] ??
widget.faas.lname,
address: offlineBldgEditKey.currentState!.value['address'] ?? widget.faas.address,
telno: offlineBldgEditKey.currentState!.value['tel_no'] ?? widget.faas.telno,
tin: offlineBldgEditKey.currentState!.value['tin'] ?? widget.faas.tin,
adminUser: offlineBldgEditKey.currentState!.value['benificiary'] ?? widget.faas.adminUser,
adminAddress: offlineBldgEditKey.currentState!.value['benificiary_address'] ?? widget.faas.adminAddress,
adminTin: offlineBldgEditKey.currentState!.value['benificiary_tin'] ?? widget.faas.adminTin,
adminTelno: offlineBldgEditKey.currentState!.value['benificiary_telno'] ?? widget.faas.adminTelno,
faasType: "Building");
context.read<CrudBloc>().add(
UpdatePropertyOwnerInfo(
id: widget.faas.id!,
propertyInfo: property_info));
context.read<CrudBloc>().add(
UpdatePropertyOwnerInfo(
id: widget.faas.id!,
propertyInfo: property_info));
widget.NextBtn();
},
),
),
])),
],
),
),
),
],
widget.NextBtn();
},
),
),
])),
],
),
),
);
}

View File

@ -47,13 +47,13 @@ class _StructuralMaterialsPageEditOffline
StructuralMaterialOfflineState>(listener: (context, state) {
if (state is SpecificStructuralMaterialLoaded) {
setState(() {
// foundation = state.materials.foundation?.split(', ') ?? [];
// column = state.materials.columns?.split(', ') ?? [];
// beam = state.materials.beams?.split(', ') ?? [];
// truss_framing = state.materials.trussFraming?.split(', ') ?? [];
// roof = state.materials.roof?.split(', ') ?? [];
// flooring = state.materials.flooring?.split(', ') ?? [];
// walls = state.materials.walls?.split(', ') ?? [];
foundation = state.materials.foundation?.split(', ') ?? [];
column = state.materials.columns?.split(', ') ?? [];
beam = state.materials.beams?.split(', ') ?? [];
truss_framing = state.materials.trussFraming?.split(', ') ?? [];
roof = state.materials.roof?.split(', ') ?? [];
flooring = state.materials.flooring?.split(', ') ?? [];
walls = state.materials.walls?.split(', ') ?? [];
// Update other local state variables here if needed
});
}
@ -103,8 +103,8 @@ class _StructuralMaterialsPageEditOffline
padding: const EdgeInsets.only(top: 10.0, bottom: 10.0),
child: Visibility(
visible: foundationOthers,
child: customTextField(
"Enter other foundation", "", "other_foundation"),
child: customTextField("Enter other foundation", "",
"other_foundation", TextInputType.text),
replacement: DropDownMultiSelect(
selected_values_style: TextStyle(color: Colors.black),
onChanged: (List<String> x) {
@ -145,8 +145,8 @@ class _StructuralMaterialsPageEditOffline
padding: const EdgeInsets.only(top: 10.0, bottom: 10.0),
child: Visibility(
visible: columOthers,
child: customTextField(
"Enter other columns", "", "other_column"),
child: customTextField("Enter other columns", "",
"other_column", TextInputType.text),
replacement: DropDownMultiSelect(
selected_values_style: TextStyle(color: Colors.black),
onChanged: (List<String> x) {
@ -186,8 +186,8 @@ class _StructuralMaterialsPageEditOffline
padding: const EdgeInsets.only(top: 10.0, bottom: 10.0),
child: Visibility(
visible: beamsOthers,
child:
customTextField("Enter other beam/s", "", "other_beam"),
child: customTextField("Enter other beam/s", "",
"other_beam", TextInputType.text),
replacement: DropDownMultiSelect(
selected_values_style: TextStyle(color: Colors.black),
onChanged: (List<String> x) {
@ -227,8 +227,8 @@ class _StructuralMaterialsPageEditOffline
padding: const EdgeInsets.only(top: 10.0, bottom: 10.0),
child: Visibility(
visible: tfOthers,
child: customTextField(
"Enter other truss framing/s", "", "other_tf"),
child: customTextField("Enter other truss framing/s", "",
"other_tf", TextInputType.text),
replacement: DropDownMultiSelect(
selected_values_style: TextStyle(color: Colors.black),
onChanged: (List<String> x) {
@ -269,8 +269,8 @@ class _StructuralMaterialsPageEditOffline
padding: const EdgeInsets.only(top: 10.0, bottom: 10.0),
child: Visibility(
visible: roofOthers,
child:
customTextField("Enter other roof/s", "", "other_roof"),
child: customTextField("Enter other roof/s", "",
"other_roof", TextInputType.text),
replacement: DropDownMultiSelect(
selected_values_style: TextStyle(color: Colors.black),
onChanged: (List<String> x) {
@ -319,8 +319,8 @@ class _StructuralMaterialsPageEditOffline
padding: const EdgeInsets.only(top: 10.0, bottom: 10.0),
child: Visibility(
visible: flooringOthers,
child: customTextField(
"Enter other flooring/s", "", "other_flooring"),
child: customTextField("Enter other flooring/s", "",
"other_flooring", TextInputType.text),
replacement: DropDownMultiSelect(
selected_values_style: TextStyle(color: Colors.black),
onChanged: (List<String> x) {
@ -367,8 +367,8 @@ class _StructuralMaterialsPageEditOffline
padding: const EdgeInsets.only(top: 10.0, bottom: 10.0),
child: Visibility(
visible: wpOthers,
child: customTextField(
"Enter other walls & partition/s", "", "other_wp"),
child: customTextField("Enter other walls & partition/s",
"", "other_wp", TextInputType.text),
replacement: DropDownMultiSelect(
selected_values_style: TextStyle(color: Colors.black),
onChanged: (List<String> x) {
@ -412,40 +412,48 @@ class _StructuralMaterialsPageEditOffline
foundation: foundationOthers
? offlineBldgEditKey
.currentState!.value['other_foundation']
.split(',')
: foundation,
: foundation.isNotEmpty
? foundation
: [state.materials.foundation!],
columns: columOthers
? offlineBldgEditKey
.currentState!.value['other_column']
.split(',')
: column,
: column.isNotEmpty
? column
: [state.materials.columns!],
beams: beamsOthers
? offlineBldgEditKey
.currentState!.value['other_beam']
.split(',')
: beam,
: beam.isNotEmpty
? beam
: [state.materials.beams!],
trussFraming: tfOthers
? offlineBldgEditKey
.currentState!.value['other_tf']
.split(',')
: truss_framing,
: truss_framing.isNotEmpty
? truss_framing
: [state.materials.trussFraming!],
roof: roofOthers
? offlineBldgEditKey
.currentState!.value['other_roof']
.split(',')
: roof,
: roof.isNotEmpty
? roof
: [state.materials.roof!],
flooring: flooringOthers
? offlineBldgEditKey
.currentState!.value['other_flooring']
.split(',')
: flooring,
: flooring.isNotEmpty
? flooring
: [state.materials.flooring!],
walls: wpOthers
? offlineBldgEditKey
.currentState!.value['other_wp']
.split(',')
: walls,
: walls.isNotEmpty
? walls
: [state.materials.walls!],
others: ["Others"]);
print('struct mat');
print(strucMaterials.toJson());
context.read<StructuralMaterialOfflineBloc>().add(
UpdateStructuralMaterials(
id: widget.tempId, materials: strucMaterials));

View File

@ -31,6 +31,8 @@ import 'package:unit2/model/passo/property_appraisal.dart';
import 'package:unit2/model/passo/property_assessment.dart';
import 'package:unit2/model/passo/property_info.dart';
import 'package:unit2/screens/offline/passo/building/add/add_building.dart';
import 'package:unit2/screens/offline/passo/building/add/drawing_pad.dart';
import 'package:unit2/screens/offline/passo/building/add/flutter_painter.dart';
import 'package:unit2/screens/offline/passo/building/edit/edit_building.dart';
import 'package:unit2/screens/offline/passo/land/add/add_land.dart';
import 'package:unit2/theme-data.dart/colors.dart';
@ -100,10 +102,14 @@ class BuildingHomeOffline extends StatelessWidget {
// 'actualUse', state.gendesc.actualUse!);
// }
// if (state is GenDescErrorState) {
// final progress = ProgressHUD.of(context);
// progress?.dismiss();
// }
if (state is PropertyInfoLoaded) {
final progress = ProgressHUD.of(context);
progress?.dismiss();
}
if (state is PropertyOwnerInfoErrorState) {
final progress = ProgressHUD.of(context);
progress?.dismiss();
}
},
builder: (context, state) {
if (state is PropertyInfoLoaded) {
@ -123,7 +129,8 @@ class BuildingHomeOffline extends StatelessWidget {
index,
deleteItem,
state.propertyInfos.length,
offlineProfile);
offlineProfile,
triggerLoadBldgFaas);
},
),
),
@ -136,6 +143,20 @@ class BuildingHomeOffline extends StatelessWidget {
"You don't have any building faas added. Please click + to add");
}
}
if (state is PropertyOwnerInfoErrorState) {
WidgetsBinding.instance.addPostFrameCallback((_) {
// Perform actions after the current build frame; safe place for setState or context-dependent actions
confirmAlertWithCancelCustom(
context,
() => context.read<CrudBloc>().add(
UploadBuildingFaas(offlineProfile: offlineProfile)),
() => context.read<CrudBloc>().add(FetchTodos()),
"Sync unsuccesful!",
"Please try again!",
"Retry",
"Cancel");
});
}
return Container();
},
)),
@ -290,7 +311,13 @@ class BuildingHomeOffline extends StatelessWidget {
color: primary,
),
label: 'Machinery',
onTap: () {},
onTap: () {
Navigator.push(
context,
MaterialPageRoute(
builder: (context) => const DrawingScreen()),
);
},
),
SpeedDialChild(
child: const Icon(
@ -310,7 +337,7 @@ class BuildingHomeOffline extends StatelessWidget {
}
Card _listCard(PropertyInfo property_info, context, index, deleteItem,
bldgLength, offlineProfile) {
bldgLength, offlineProfile, triggerLoadLandFaas) {
return Card(
shape: RoundedRectangleBorder(
borderRadius: BorderRadius.circular(10),
@ -390,7 +417,8 @@ Card _listCard(PropertyInfo property_info, context, index, deleteItem,
index: index,
faas: property_info,
title: 'Bldg & Structure Edit',
offlineProfile: offlineProfile),
offlineProfile: offlineProfile,
loadBldg: triggerLoadLandFaas),
);
}));
},
@ -429,7 +457,14 @@ Card _listCard(PropertyInfo property_info, context, index, deleteItem,
),
SizedBox(height: 5),
Text(
'${property_info.tdn}',
'TDN: ${property_info.tdn}',
style: TextStyle(
fontSize: 13,
),
textAlign: TextAlign.left,
),
Text(
'Uploaded on: ${property_info.dateSynced == null ? '--' : property_info.dateSynced}',
style: TextStyle(
fontSize: 13,
),

View File

@ -366,7 +366,8 @@ class _AddLandAppraisalOfflineModal
},
style:
ElevatedButton.styleFrom(
primary: Colors.black,
backgroundColor:
Colors.black,
),
child: const Text("Submit"),
),
@ -389,7 +390,8 @@ class _AddLandAppraisalOfflineModal
},
style:
ElevatedButton.styleFrom(
primary: Colors.black,
backgroundColor:
Colors.black,
),
child: const Text("Cancel"),
),

View File

@ -291,7 +291,7 @@ class _AddPropertyAssessmentOfflineModal
totalAssessedval: '0'));
},
style: ElevatedButton.styleFrom(
primary: Colors.black,
backgroundColor: Colors.black,
),
child: const Text("Submit"),
),
@ -311,7 +311,7 @@ class _AddPropertyAssessmentOfflineModal
const LoadLandPropertyAssessment());
},
style: ElevatedButton.styleFrom(
primary: Colors.black,
backgroundColor: Colors.black,
),
child: const Text("Cancel"),
),

View File

@ -305,7 +305,7 @@ class _AddOtherImprovementModalOffline
));
},
style: ElevatedButton.styleFrom(
primary: Colors.black,
backgroundColor: Colors.black,
),
child: const Text("Submit"),
),
@ -324,7 +324,7 @@ class _AddOtherImprovementModalOffline
.add(const LoadOtherImprovements());
},
style: ElevatedButton.styleFrom(
primary: Colors.black,
backgroundColor: Colors.black,
),
child: const Text("Cancel"),
),

View File

@ -434,7 +434,8 @@ class _AddLandValueAdjustmentOfflineModal
},
style:
ElevatedButton.styleFrom(
primary: Colors.black,
backgroundColor:
Colors.black,
),
child: const Text("Submit"),
),
@ -457,7 +458,8 @@ class _AddLandValueAdjustmentOfflineModal
},
style:
ElevatedButton.styleFrom(
primary: Colors.black,
backgroundColor:
Colors.black,
),
child: const Text("Cancel"),
),

View File

@ -36,24 +36,30 @@ class _LandPropertyOwnerInfoOffline
const SizedBox(height: 15),
customDropDownField(
"Transaction Code", "", "transaction_code", transaction_codes),
customTextField("ARP No./ TD No.", "", "td_no"),
customTextField("Owner", "", "owner"),
customTextField(
"ARP No./ TD No.", "", "td_no", TextInputType.number),
customTextField("Owner", "", "owner", TextInputType.text),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(flex: 1, child: customTextField("PIN", "", "pin")),
Expanded(
flex: 1,
child: customTextField(
"PIN", "", "pin", TextInputType.number)),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField("TIN", "", "tin"))
child: customTextField(
"TIN", "", "tin", TextInputType.number))
]),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField("OCT/TCT CLOA No.", "", "cloa_no"),
child: customTextField("OCT/TCT CLOA No.", "", "cloa_no",
TextInputType.number),
),
const SizedBox(width: 10.0),
Expanded(
@ -66,31 +72,21 @@ class _LandPropertyOwnerInfoOffline
children: <Widget>[
Expanded(
flex: 1,
child: customTextField("Survey No.", "", "survey_no"),
child: customTextField(
"Survey No.", "", "survey_no", TextInputType.number),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField("Lot No.", "", "lot_no")),
child: customTextField(
"Lot No.", "", "lot_no", TextInputType.number)),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField("Blk", "", "blk")),
]),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField("Address", "", "address"),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField("Tel No.", "", "tel_no"))
child: customTextField(
"Blk", "", "blk", TextInputType.number)),
]),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
@ -98,26 +94,44 @@ class _LandPropertyOwnerInfoOffline
Expanded(
flex: 1,
child: customTextField(
"Administrator/Beneficial User", "", "admin"),
"Address", "", "address", TextInputType.text),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField("TIN", "", "admin_tin"))
child: customTextField(
"Tel No.", "", "tel_no", TextInputType.number))
]),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField("Address", "", "admin_address"),
child: customTextField("Administrator/Beneficial User", "",
"admin", TextInputType.text),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField("Tel No.", "", "admin_telno"))
child: customTextField(
"TIN", "", "admin_tin", TextInputType.number))
]),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField(
"Address", "", "admin_address", TextInputType.text),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField(
"Tel No.", "", "admin_telno", TextInputType.number))
]),
SizedBox(
height: 30,

View File

@ -57,14 +57,14 @@ class _LandLocationAndBoundariesOffline
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField(
"No. / Street", "", "street")),
child: customTextField("No. / Street", "",
"street", TextInputType.text)),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField(
"Brgy./District", "", "brgy")),
child: customTextField("Brgy./District", "",
"brgy", TextInputType.text)),
],
),
Row(
@ -72,15 +72,15 @@ class _LandLocationAndBoundariesOffline
children: <Widget>[
Expanded(
flex: 1,
child: customTextField(
"Municipality", "", "municipality"),
child: customTextField("Municipality", "",
"municipality", TextInputType.text),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField(
"Province/City", "", "province"))
child: customTextField("Province/City", "",
"province", TextInputType.text))
]),
Container(
margin: const EdgeInsets.only(
@ -95,26 +95,30 @@ class _LandLocationAndBoundariesOffline
children: <Widget>[
Expanded(
flex: 1,
child: customTextField("North", "", "north"),
child: customTextField(
"North", "", "north", TextInputType.text),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField("East", "", "east"))
child: customTextField(
"East", "", "east", TextInputType.text))
]),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField("South", "", "south"),
child: customTextField(
"South", "", "south", TextInputType.text),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField("West", "", "west"))
child: customTextField(
"West", "", "west", TextInputType.text))
]),
SizedBox(
height: 50,

View File

@ -343,7 +343,8 @@ class _AddLandAppraisalEditOfflineModal
},
style:
ElevatedButton.styleFrom(
primary: Colors.black,
backgroundColor:
Colors.black,
),
child: const Text("Submit"),
),
@ -366,7 +367,8 @@ class _AddLandAppraisalEditOfflineModal
},
style:
ElevatedButton.styleFrom(
primary: Colors.black,
backgroundColor:
Colors.black,
),
child: const Text("Cancel"),
),

View File

@ -302,7 +302,7 @@ class _AddOtherImprovementModalEditOffline
));
},
style: ElevatedButton.styleFrom(
primary: Colors.black,
backgroundColor: Colors.black,
),
child: const Text("Submit"),
),
@ -321,7 +321,7 @@ class _AddOtherImprovementModalEditOffline
.add(const LoadOtherImprovements());
},
style: ElevatedButton.styleFrom(
primary: Colors.black,
backgroundColor: Colors.black,
),
child: const Text("Cancel"),
),

View File

@ -290,7 +290,7 @@ class _AddPropertyAssessmentEditOfflineModal
totalAssessedval: '0'));
},
style: ElevatedButton.styleFrom(
primary: Colors.black,
backgroundColor: Colors.black,
),
child: const Text("Submit"),
),
@ -310,7 +310,7 @@ class _AddPropertyAssessmentEditOfflineModal
const LoadLandPropertyAssessment());
},
style: ElevatedButton.styleFrom(
primary: Colors.black,
backgroundColor: Colors.black,
),
child: const Text("Cancel"),
),

View File

@ -433,7 +433,8 @@ class _AddLandValueAdjustmentEditOfflineModal
},
style:
ElevatedButton.styleFrom(
primary: Colors.black,
backgroundColor:
Colors.black,
),
child: const Text("Submit"),
),
@ -456,7 +457,8 @@ class _AddLandValueAdjustmentEditOfflineModal
},
style:
ElevatedButton.styleFrom(
primary: Colors.black,
backgroundColor:
Colors.black,
),
child: const Text("Cancel"),
),

View File

@ -71,26 +71,30 @@ class _LandPropertyOwnerInfoOfflineEdit
const SizedBox(height: 15),
customDropDownField("Transaction Code", "",
"transaction_code", transaction_codes),
customTextField("ARP No./ TD No.", "", "td_no"),
customTextField("Owner", "", "owner"),
customTextField(
"ARP No./ TD No.", "", "td_no", TextInputType.number),
customTextField("Owner", "", "owner", TextInputType.text),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1, child: customTextField("PIN", "", "pin")),
flex: 1,
child: customTextField(
"PIN", "", "pin", TextInputType.number)),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField("TIN", "", "tin"))
child: customTextField(
"TIN", "", "tin", TextInputType.number))
]),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField(
"OCT/TCT CLOA No.", "", "cloa_no"),
child: customTextField("OCT/TCT CLOA No.", "",
"cloa_no", TextInputType.number),
),
const SizedBox(width: 10.0),
Expanded(
@ -103,31 +107,21 @@ class _LandPropertyOwnerInfoOfflineEdit
children: <Widget>[
Expanded(
flex: 1,
child: customTextField("Survey No.", "", "survey_no"),
child: customTextField("Survey No.", "", "survey_no",
TextInputType.number),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField("Lot No.", "", "lot_no")),
child: customTextField(
"Lot No.", "", "lot_no", TextInputType.number)),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField("Blk", "", "blk")),
]),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField("Address", "", "address"),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField("Tel No.", "", "tel_no"))
child: customTextField(
"Blk", "", "blk", TextInputType.number)),
]),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
@ -135,28 +129,47 @@ class _LandPropertyOwnerInfoOfflineEdit
Expanded(
flex: 1,
child: customTextField(
"Administrator/Beneficial User", "", "admin"),
"Address", "", "address", TextInputType.text),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField("TIN", "", "admin_tin"))
child: customTextField(
"Tel No.", "", "tel_no", TextInputType.number))
]),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child:
customTextField("Address", "", "admin_address"),
child: customTextField(
"Administrator/Beneficial User",
"",
"admin",
TextInputType.text),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child:
customTextField("Tel No.", "", "admin_telno"))
child: customTextField(
"TIN", "", "admin_tin", TextInputType.number))
]),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: <Widget>[
Expanded(
flex: 1,
child: customTextField("Address", "", "admin_address",
TextInputType.text),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField("Tel No.", "", "admin_telno",
TextInputType.number))
]),
SizedBox(
height: 30,

View File

@ -96,14 +96,14 @@ class _LandLocationAndBoundariesOfflineEdit
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField(
"No. / Street", "", "street")),
child: customTextField("No. / Street",
"", "street", TextInputType.text)),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField(
"Brgy./District", "", "brgy")),
child: customTextField("Brgy./District",
"", "brgy", TextInputType.text)),
],
),
Row(
@ -113,14 +113,20 @@ class _LandLocationAndBoundariesOfflineEdit
Expanded(
flex: 1,
child: customTextField(
"Municipality", "", "municipality"),
"Municipality",
"",
"municipality",
TextInputType.text),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField(
"Province/City", "", "province"))
"Province/City",
"",
"province",
TextInputType.text))
]),
Container(
margin: const EdgeInsets.only(
@ -137,15 +143,15 @@ class _LandLocationAndBoundariesOfflineEdit
children: <Widget>[
Expanded(
flex: 1,
child: customTextField(
"North", "", "north"),
child: customTextField("North", "",
"north", TextInputType.text),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField(
"East", "", "east"))
child: customTextField("East", "",
"east", TextInputType.text))
]),
Row(
mainAxisAlignment:
@ -153,15 +159,15 @@ class _LandLocationAndBoundariesOfflineEdit
children: <Widget>[
Expanded(
flex: 1,
child: customTextField(
"South", "", "south"),
child: customTextField("South", "",
"south", TextInputType.text),
),
const SizedBox(width: 10.0),
Expanded(
// optional flex property if flex is 1 because the default flex is 1
flex: 1,
child: customTextField(
"West", "", "west"))
child: customTextField("West", "",
"west", TextInputType.text))
]),
const SizedBox(
height: 50,

View File

@ -19,7 +19,7 @@ class PassoOfflineMainScreen extends StatelessWidget {
return Scaffold(
appBar: AppBar(
backgroundColor: primary,
title: const Text("PASSO Offlne Home"),
title: const Text("Rpass Offline Home"),
centerTitle: true,
),
body: Padding(
@ -50,15 +50,6 @@ class PassoOfflineMainScreen extends StatelessWidget {
return PassoOfflineDashBoard(offlineProfile);
})));
}),
CardLabel(
icon: FontAwesome5.tools,
title: "Super Admin",
ontap: () {
Navigator.push(context,
MaterialPageRoute(builder: ((context) {
return PassoOfflineDashBoard(offlineProfile);
})));
})
])));
}
}

View File

@ -68,7 +68,7 @@ class AddMobile extends StatelessWidget {
),
Text(addMobileCaption,
textAlign: TextAlign.center,
style: Theme.of(context).textTheme.caption),
style: Theme.of(context).textTheme.bodyMedium),
const SizedBox(
height: 24,
),
@ -81,16 +81,16 @@ class AddMobile extends StatelessWidget {
name: 'mobile1',
validator: mobileNumberValidator,
maxLength: 11,
decoration:
normalTextFieldStyle(mobile1, "sfdfsdfsd")),
decoration: normalTextFieldStyle(
mobile1, "sfdfsdfsd")),
const SizedBox(
height: 12,
),
FormBuilderTextField(
name: 'mobile2',
maxLength: 11,
decoration:
normalTextFieldStyle(mobile2, "0900000000000")),
decoration: normalTextFieldStyle(
mobile2, "0900000000000")),
SizedBox(
height: isMobile()
@ -108,9 +108,7 @@ class AddMobile extends StatelessWidget {
),
onPressed: () {
if (_formKey.currentState!
.saveAndValidate()) {
}
.saveAndValidate()) {}
// }
},

View File

@ -11,113 +11,115 @@ import '../../../utils/global.dart';
class SosAcknowledged extends StatelessWidget {
final Function() onpressed;
final SessionData sessionData;
const SosAcknowledged({super.key, required this.onpressed, required this.sessionData});
const SosAcknowledged(
{super.key, required this.onpressed, required this.sessionData});
@override
Widget build(BuildContext context) {
return Container(
padding: const EdgeInsets.symmetric(vertical: 40, horizontal: 35),
height: screenHeight,
child: Stack(
children: [
Positioned(
bottom: 0,
return Container(
padding: const EdgeInsets.symmetric(vertical: 40, horizontal: 35),
height: screenHeight,
child: Stack(
children: [
Positioned(
bottom: 0,
child: SizedBox(
width: screenWidth,
height: screenHeight / 2,
child: Opacity(
opacity: .2,
child: Image.asset(
"assets/pngs/emergency.png",
fit: BoxFit.cover,
),
),
)),
Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
const SizedBox(
height: 18,
),
SlideInDown(
child: AutoSizeText(
"SOS Acknowledged!",
maxLines: 2,
textAlign: TextAlign.center,
style: Theme.of(context).textTheme.displayMedium!.copyWith(
fontSize: 40,
color: success2,
fontWeight: FontWeight.w600),
),
),
const SizedBox(
height: 5,
),
SlideInDown(
child: const Icon(
Iconic.ok_circle,
color: success2,
size: 120,
),
),
const SizedBox(
height: 22,
),
SlideInUp(
child: Container(
decoration: const BoxDecoration(
color: Colors.white,
borderRadius: BorderRadius.all(Radius.circular(15))),
child: Column(
children: [
ListTile(
title: AutoSizeText(
sessionData.acknowledgedBy!.toUpperCase(),
maxLines: 2,
style: Theme.of(context)
.textTheme
.headlineMedium!
.copyWith(
fontSize: 22,
fontWeight: FontWeight.bold,
color: third),
),
subtitle: Text(
"Acknowledge by",
style: Theme.of(context).textTheme.labelLarge,
),
),
Container(
padding: const EdgeInsets.all(15),
child: Text(
"NOTE: Please ensure that the mobile numbers you provided are still active, and look for an area with stable network. The response team will contact your mobile number.",
textAlign: TextAlign.justify,
style:
Theme.of(context).textTheme.bodyMedium!.copyWith(
fontSize: 14,
color: Colors.black87,
),
),
),
],
),
),
),
Expanded(child: Container()),
SlideInUp(
child: SizedBox(
width: screenWidth,
height: screenHeight / 2,
child: Opacity(
opacity: .2,
child: Image.asset(
"assets/pngs/emergency.png",
fit: BoxFit.cover,
),
),
)),
Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
const SizedBox(
height: 18,
height: 50,
width: double.infinity,
child: ElevatedButton(
style: mainBtnStyle(
second, Colors.transparent, Colors.white54),
onPressed: onpressed,
child: const Text("DONE!")),
),
SlideInDown(
child: AutoSizeText(
"SOS Acknowledged!",
maxLines: 2,
textAlign: TextAlign.center,
style: Theme.of(context).textTheme.displayMedium!.copyWith(
fontSize: 40,
color: success2,
fontWeight: FontWeight.w600),
),
),
const SizedBox(
height: 5,
),
SlideInDown(
child: const Icon(
Iconic.ok_circle,
color: success2,
size: 120,
),
),
const SizedBox(
height: 22,
),
SlideInUp(
child: Container(
decoration: const BoxDecoration(
color: Colors.white,
borderRadius: BorderRadius.all(Radius.circular(15))),
child: Column(
children: [
ListTile(
title: AutoSizeText(
sessionData.acknowledgedBy!.toUpperCase(),
maxLines: 2,
style: Theme.of(context).textTheme.headline4!.copyWith(
fontSize: 22,
fontWeight: FontWeight.bold,
color: third),
),
subtitle: Text(
"Acknowledge by",
style: Theme.of(context).textTheme.labelLarge,
),
),
Container(
padding: const EdgeInsets.all(15),
child: Text(
"NOTE: Please ensure that the mobile numbers you provided are still active, and look for an area with stable network. The response team will contact your mobile number.",
textAlign: TextAlign.justify,
style: Theme.of(context).textTheme.caption!.copyWith(
fontSize: 14,
color: Colors.black87,
),
),
),
],
),
),
),
Expanded(child: Container()),
SlideInUp(
child: SizedBox(
height: 50,
width: double.infinity,
child: ElevatedButton(
style:
mainBtnStyle(second, Colors.transparent, Colors.white54),
onPressed: onpressed,
child: const Text("DONE!")),
),
)
],
),
],
),
)
],
),
],
),
);
}
}

View File

@ -24,7 +24,7 @@ class Mobile extends StatelessWidget {
title: Text(title),
subtitle: Text(
subtitle,
style: Theme.of(context).textTheme.caption,
style: Theme.of(context).textTheme.bodyMedium,
),
trailing: IconButton(
icon: const Icon(Icons.edit),

View File

@ -10,124 +10,123 @@ import '../../../utils/global.dart';
class SOSreceived extends StatelessWidget {
final Function() onpressed;
const SOSreceived({super.key, required this.onpressed});
const SOSreceived({super.key, required this.onpressed});
@override
Widget build(BuildContext context) {
return Container(
padding: const EdgeInsets.symmetric(vertical: 40, horizontal: 35),
height: screenHeight,
child: Stack(
children: [
Positioned(
bottom: 0,
child: SizedBox(
width: screenWidth,
height: screenHeight / 2,
child: Opacity(
opacity: .2,
child: Image.asset(
"assets/pngs/emergency.png",
fit: BoxFit.cover,
),
),
)),
Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
SizedBox(
height: blockSizeVertical * 6,
),
Bounce(
from: 20,
infinite: true,
delay: const Duration(milliseconds: 800),
child: Stack(
alignment: AlignmentDirectional.topCenter,
children: [
Container(
margin: const EdgeInsets.only(top: 20),
child: CircleAvatar(
radius: blockSizeVertical * 8,
backgroundColor: second,
child: Container(
margin: const EdgeInsets.only(top: 25),
child: SvgPicture.asset(
'assets/svgs/sos.svg',
height: blockSizeHorizontal * 17,
color: Colors.white,
allowDrawingOutsideViewBox: true,
alignment: Alignment.bottomCenter,
),
),
),
),
Positioned(
top: blockSizeVertical * 3,
child: const SpinKitPulse(
color: primary,
size: 120,
),
),
],
return Container(
padding: const EdgeInsets.symmetric(vertical: 40, horizontal: 35),
height: screenHeight,
child: Stack(
children: [
Positioned(
bottom: 0,
child: SizedBox(
width: screenWidth,
height: screenHeight / 2,
child: Opacity(
opacity: .2,
child: Image.asset(
"assets/pngs/emergency.png",
fit: BoxFit.cover,
),
),
const SizedBox(height: 16),
SlideInUp(
from: 50,
child: AutoSizeText(
sosReceived,
textAlign: TextAlign.center,
style: Theme.of(context).textTheme.displayMedium!.copyWith(
fontSize: 40,
color: third,
fontWeight: FontWeight.w500,
),
),
),
const SizedBox(
height: 8,
),
SlideInUp(
from: 50,
child: Container(
padding: const EdgeInsets.all(15),
decoration: const BoxDecoration(
color: Colors.white,
borderRadius: BorderRadius.all(Radius.circular(15))),
child: AutoSizeText(
sOSReceivedMessage,
textAlign: TextAlign.center,
style: Theme.of(context).textTheme.caption!.copyWith(
fontSize: 16,
color: Colors.black87,
),
),
),
),
const SizedBox(
height: 40,
),
Expanded(child: Container()),
SlideInUp(
child: SizedBox(
height: 50,
width: 200,
child: TextButton(
style: mainBtnStyle(second, Colors.transparent, second),
onPressed: onpressed,
child: const Text(cancelRequest,
style: TextStyle(
)),
Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
SizedBox(
height: blockSizeVertical * 6,
),
Bounce(
from: 20,
infinite: true,
delay: const Duration(milliseconds: 800),
child: Stack(
alignment: AlignmentDirectional.topCenter,
children: [
Container(
margin: const EdgeInsets.only(top: 20),
child: CircleAvatar(
radius: blockSizeVertical * 8,
backgroundColor: second,
child: Container(
margin: const EdgeInsets.only(top: 25),
child: SvgPicture.asset(
'assets/svgs/sos.svg',
height: blockSizeHorizontal * 17,
color: Colors.white,
)),
allowDrawingOutsideViewBox: true,
alignment: Alignment.bottomCenter,
),
),
),
),
Positioned(
top: blockSizeVertical * 3,
child: const SpinKitPulse(
color: primary,
size: 120,
),
),
],
),
),
const SizedBox(height: 16),
SlideInUp(
from: 50,
child: AutoSizeText(
sosReceived,
textAlign: TextAlign.center,
style: Theme.of(context).textTheme.displayMedium!.copyWith(
fontSize: 40,
color: third,
fontWeight: FontWeight.w500,
),
),
),
const SizedBox(
height: 8,
),
SlideInUp(
from: 50,
child: Container(
padding: const EdgeInsets.all(15),
decoration: const BoxDecoration(
color: Colors.white,
borderRadius: BorderRadius.all(Radius.circular(15))),
child: AutoSizeText(
sOSReceivedMessage,
textAlign: TextAlign.center,
style: Theme.of(context).textTheme.bodyMedium!.copyWith(
fontSize: 16,
color: Colors.black87,
),
),
)
],
),
],
),
),
),
const SizedBox(
height: 40,
),
Expanded(child: Container()),
SlideInUp(
child: SizedBox(
height: 50,
width: 200,
child: TextButton(
style: mainBtnStyle(second, Colors.transparent, second),
onPressed: onpressed,
child: const Text(cancelRequest,
style: TextStyle(
color: Colors.white,
)),
),
),
)
],
),
],
),
);
}
}

View File

@ -43,7 +43,7 @@ class NoModule extends StatelessWidget {
noModuleSubTitle,
style: Theme.of(context)
.textTheme
.caption!
.bodySmall!
.copyWith(fontSize: blockSizeVertical * 1.5),
textAlign: TextAlign.center,
)

View File

@ -138,7 +138,7 @@ class _UniT2LoginState extends State<UniT2Login> {
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
SvgPicture.asset(
'assets/svgs/logo.svg',
'assets/svgs/rpass_logo.svg',
height: blockSizeVertical * 12,
allowDrawingOutsideViewBox: true,
color: primary,

View File

@ -5,7 +5,8 @@ import '../../../../../theme-data.dart/colors.dart';
class SelectedState extends StatelessWidget {
final String title;
final String subtitle;
const SelectedState({Key? key,required this.subtitle, required this.title}) : super(key: key);
const SelectedState({Key? key, required this.subtitle, required this.title})
: super(key: key);
@override
Widget build(BuildContext context) {
@ -24,7 +25,7 @@ class SelectedState extends StatelessWidget {
Text(
title,
textAlign: TextAlign.center,
style: Theme.of(context).textTheme.button!.copyWith(
style: Theme.of(context).textTheme.titleMedium!.copyWith(
color: third, fontWeight: FontWeight.bold, fontSize: 18),
),
Text(
@ -32,7 +33,6 @@ class SelectedState extends StatelessWidget {
style: Theme.of(context).textTheme.labelMedium,
),
const Divider(),
]),
],
),

View File

@ -82,7 +82,7 @@ class _ViewListState extends State<ViewList> {
dense: true,
subtitle: Text(
"December 15 1994",
style: Theme.of(context).textTheme.caption,
style: Theme.of(context).textTheme.bodyMedium,
),
leading: Checkbox(
onChanged: (value) {

View File

@ -22,6 +22,7 @@ import '../../../../../model/passo/additional_items.dart';
import '../../../../../model/passo/barangay.dart';
import '../../../../../model/passo/building_and_structure.dart';
import '../../../../../model/passo/class_components _offline.dart';
import '../../../../../model/passo/floor_sketch.dart';
import '../../../../../model/passo/general_description.dart';
import '../../../../../model/passo/land_appr.dart';
import '../../../../../model/passo/land_classification.dart';
@ -116,7 +117,7 @@ class SQLServices {
firstname TEXT NOT NULL,
middlename TEXT NOT NULL,
lastname TEXT NOT NULL,
designation TEXT
designation TEXT NOT NULL
)
''');
@ -178,6 +179,16 @@ class SQLServices {
)
''');
await db.execute('''
CREATE TABLE bldg_floor_sketch (
id INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL,
bldgappr_details_id INTEGER NOT NULL,
date_created TEXT NOT NULL,
floor_sketch TEXT NOT NULL,
gen_code TEXT NOT NULL
)
''');
await db.execute('''
CREATE TABLE value_adjustments (
id INTEGER PRIMARY KEY AUTOINCREMENT NOT NULL,
@ -213,7 +224,8 @@ class SQLServices {
assessedByName TEXT NOT NULL,
dateCreated TEXT NOT NULL,
dateModified TEXT NOT NULL,
gen_code TEXT
gen_code TEXT,
dateSynced TEXT
)
''');
@ -303,7 +315,8 @@ class SQLServices {
marketValue TEXT NOT NULL,
depAmount TEXT NOT NULL,
adjustedMarketValue TEXT NOT NULL,
gen_code TEXT
gen_code TEXT,
dateSync TEXT
)
''');
@ -373,6 +386,7 @@ class SQLServices {
recommendappr_designation TEXT,
approvedbyName TEXT NOT NULL,
approvedby_designation TEXT,
approvedbyDate TEXT,
memoranda TEXT NOT NULL,
swornstatementNo TEXT NOT NULL,
dateReceived TEXT NOT NULL,
@ -402,7 +416,8 @@ class SQLServices {
paintedUnitval TEXT NOT NULL,
secondhandUnitval TEXT NOT NULL,
actualUse TEXT NOT NULL,
gen_code TEXT
gen_code TEXT,
dateSync TEXT
)
''');
@ -931,6 +946,7 @@ class SQLServices {
"assessedByName": propertyInfo.assessedByName,
"dateCreated": "000",
"dateModified": "000",
"dateSynced": propertyInfo.dateSynced
};
final result =
@ -1178,6 +1194,32 @@ class SQLServices {
return result;
}
// Floor Sketch
Future<FloorSketch> createFloorSketch(FloorSketch floorSketch) async {
final db = await instance.database;
final data = {
// "id": treesImprovements.id,
"bldgappr_details_id": floorSketch.bldgapprDetailsId,
"date_created": floorSketch.dateCreated,
"floor_sketch": floorSketch.floorSketch,
"gen_code": "5TH"
};
final id = await db.insert('bldg_floor_sketch', data);
return floorSketch.copy(bldgapprDetailsId: id);
}
Future<List<Map<String, dynamic>>> getFloorSketch(id) async {
final db = await instance.database;
final results = await db.query('bldg_floor_sketch',
where: "bldgappr_details_id = ?", whereArgs: [id], limit: 1);
print('floor sketch test result');
print(results);
return results;
}
//Structural Materials
Future<StructureMaterialsII> createStructuralMaterials(
@ -1220,7 +1262,6 @@ class SQLServices {
id, StructureMaterialsII materials) async {
final db = await instance.database;
final data = {
"bldgapprDetailsId": materials.bldgapprDetailsId,
"foundation": materials.foundation?.join(', ').splitMapJoin(', '),
"columns": materials.columns!.join(', ').splitMapJoin(', '),
"beams": materials.beams!.join(', ').splitMapJoin(', '),
@ -1434,6 +1475,8 @@ class SQLServices {
Future<PropertyAssessment> createBldgAssessment(
PropertyAssessment assessment) async {
final db = await instance.database;
print('assesss');
print(assessment.toJson());
final data = {
// "id": assessment.id,
@ -1455,6 +1498,7 @@ class SQLServices {
"recommendapprName": assessment.recommendapprName,
"recommendapprDate": assessment.recommendapprDate,
"approvedbyName": assessment.approvedbyName,
"approvedbyDate": assessment.approvedbyDate,
"memoranda": assessment.memoranda,
"swornstatementNo": assessment.swornstatementNo,
"dateReceived": assessment.dateReceived,

View File

@ -0,0 +1,35 @@
import 'dart:convert';
import 'dart:developer';
import 'dart:io';
import 'package:http/http.dart' as http;
import 'package:unit2/model/passo/building_details.dart';
import 'package:unit2/model/passo/structural_materials_ii.dart';
import 'package:unit2/model/passo/structureMaterial.dart';
import 'package:unit2/utils/request.dart';
import 'package:unit2/utils/urls.dart';
class BuildingServices {
static final BuildingServices _instance = BuildingServices();
static BuildingServices get instance => _instance;
String xClientKey = "unitK3CQaXiWlPReDsBzmmwBZPd9Re1z";
String xClientKeySecret = "unitcYqAN7GGalyz";
Future<http.Response?> add(details) async {
String path = Url.instance.buildingDetails();
Map<String, String> headers = {
'Content-Type': 'application/json; charset=UTF-8',
'X-Client-Key': xClientKey,
'X-Client-Secret': xClientKeySecret
};
http.Response? response;
try {
response = await Request.instance
.postRequest(param: {}, path: path, body: details, headers: headers);
} catch (e) {
log(e.toString());
}
return response;
}
}

View File

@ -4,7 +4,7 @@ import 'package:unit2/theme-data.dart/btn-style.dart';
import 'package:unit2/theme-data.dart/colors.dart';
import 'package:unit2/utils/global.dart';
confirmAlert(context, Function() yes,String title, String subtitle) {
confirmAlert(context, Function() yes, String title, String subtitle) {
AwesomeDialog(
context: context,
dialogType: DialogType.question,
@ -37,7 +37,13 @@ confirmAlert(context, Function() yes,String title, String subtitle) {
).show();
}
confirmAlertWithCancel(context, Function() yes,Function() no,String title, String subtitle,) {
confirmAlertWithCancel(
context,
Function() yes,
Function() no,
String title,
String subtitle,
) {
AwesomeDialog(
context: context,
dialogType: DialogType.question,
@ -70,33 +76,78 @@ confirmAlertWithCancel(context, Function() yes,Function() no,String title, Strin
).show();
}
confirmAlertWithCancelCustom(context, Function() yes, Function() no,
String title, String subtitle, okText, cancelText) {
AwesomeDialog(
context: context,
dialogType: DialogType.question,
borderSide: const BorderSide(
color: Colors.green,
width: 0,
),
width: blockSizeHorizontal * 90,
buttonsBorderRadius: const BorderRadius.all(
Radius.circular(2),
),
dismissOnTouchOutside: false,
dismissOnBackKeyPress: false,
// onDismissCallback: (type) {
// ScaffoldMessenger.of(context).showSnackBar(
// SnackBar(
// content: Text('Dismissed by $type'),
// ),
// );
// },
headerAnimationLoop: false,
animType: AnimType.bottomSlide,
title: title,
desc: subtitle,
btnOkText: okText,
btnCancelText: cancelText,
showCloseIcon: false,
btnCancelOnPress: no,
btnOkOnPress: yes,
).show();
}
errorAlert(context, title, description,Function() func) {
errorAlert(context, title, description, Function() func) {
AwesomeDialog(
width: blockSizeHorizontal * 90,
context: context,
dialogType: DialogType.error,
animType: AnimType.scale,
headerAnimationLoop: false,
title: title,
desc: description,
btnOk: SizedBox(height: 50,child: ElevatedButton(onPressed:func, style: mainBtnStyle(primary, Colors.transparent, second), child: const Text("OK")), )
).show();
width: blockSizeHorizontal * 90,
context: context,
dialogType: DialogType.error,
animType: AnimType.scale,
headerAnimationLoop: false,
title: title,
desc: description,
btnOk: SizedBox(
height: 50,
child: ElevatedButton(
onPressed: func,
style: mainBtnStyle(primary, Colors.transparent, second),
child: const Text("OK")),
)).show();
}
successAlert(context, title, description,Function() func) {
successAlert(context, title, description, Function() func) {
AwesomeDialog(
width: blockSizeHorizontal * 90,
context: context,
dialogType: DialogType.success,
animType: AnimType.scale,
headerAnimationLoop: false,
title: title,
desc: description,
btnOk: SizedBox(height: 50,child: ElevatedButton(style: mainBtnStyle(success2, Colors.transparent, success), onPressed: func, child: const Text("OK")), )
).show();
width: blockSizeHorizontal * 90,
context: context,
dialogType: DialogType.success,
animType: AnimType.scale,
headerAnimationLoop: false,
title: title,
desc: description,
btnOk: SizedBox(
height: 50,
child: ElevatedButton(
style: mainBtnStyle(success2, Colors.transparent, success),
onPressed: func,
child: const Text("OK")),
)).show();
}
okAlert(context,title,description){
AwesomeDialog(
okAlert(context, title, description) {
AwesomeDialog(
width: blockSizeHorizontal * 90,
context: context,
dialogType: DialogType.error,

View File

@ -16,7 +16,7 @@ const String sOSReceivedMessage =
"your SOS request has been received. Please wait for respondent's acknowledgement.";
const String unit2ModuleScreen = "uniT Dashboard";
const String welcome = "Welcome to!";
const String unitApp = 'uniT-App';
const String unitApp = 'Rpass-App';
const String loginToContinue = "Please login to continue.";
const String loginViaQr = "Login via QR code";
const String emergencyReponseLabel = " Request Emergency Response ";

View File

@ -368,6 +368,10 @@ class Url {
return "/api/rptass_app/additional_items/";
}
String buildingDetails() {
return "/api/rptass_app/bldgappr_details/";
}
String generalDescription() {
return "/api/rptass_app/bldgappr_gendesc/";
}

View File

@ -3,11 +3,13 @@ import 'package:flutter_form_builder/flutter_form_builder.dart';
import 'package:form_builder_validators/form_builder_validators.dart';
import 'package:unit2/theme-data.dart/form-style.dart';
Widget customTextField(String labelText, String hintText, String keyText) {
Widget customTextField(
String labelText, String hintText, String keyText, TextInputType type) {
return Container(
margin: const EdgeInsets.only(left: 0, top: 10, right: 0, bottom: 0),
child: FormBuilderTextField(
name: keyText,
keyboardType: type,
decoration: normalTextFieldStyle(labelText, hintText),
validator: FormBuilderValidators.compose([]),
),

View File

@ -7,6 +7,7 @@
#include "generated_plugin_registrant.h"
#include <audioplayers_linux/audioplayers_linux_plugin.h>
#include <file_selector_linux/file_selector_plugin.h>
#include <modal_progress_hud_nsn/modal_progress_hud_nsn_plugin.h>
#include <platform_device_id_linux/platform_device_id_linux_plugin.h>
#include <url_launcher_linux/url_launcher_plugin.h>
@ -15,6 +16,9 @@ void fl_register_plugins(FlPluginRegistry* registry) {
g_autoptr(FlPluginRegistrar) audioplayers_linux_registrar =
fl_plugin_registry_get_registrar_for_plugin(registry, "AudioplayersLinuxPlugin");
audioplayers_linux_plugin_register_with_registrar(audioplayers_linux_registrar);
g_autoptr(FlPluginRegistrar) file_selector_linux_registrar =
fl_plugin_registry_get_registrar_for_plugin(registry, "FileSelectorPlugin");
file_selector_plugin_register_with_registrar(file_selector_linux_registrar);
g_autoptr(FlPluginRegistrar) modal_progress_hud_nsn_registrar =
fl_plugin_registry_get_registrar_for_plugin(registry, "ModalProgressHudNsnPlugin");
modal_progress_hud_nsn_plugin_register_with_registrar(modal_progress_hud_nsn_registrar);

Some files were not shown because too many files have changed in this diff Show More