mirror of
https://github.com/SyncrowIOT/syncrow-app.git
synced 2026-10-23 09:07:54 +00:00
@@ -0,0 +1,20 @@
|
||||
<svg width="40" height="40" viewBox="0 0 40 40" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<path d="M0 20C0 8.95416 8.95416 0 20 0C31.0458 0 40 8.95416 40 20C40 31.0458 31.0458 40 20 40C8.95416 40 0 31.0458 0 20ZM20 31.9598C26.6052 31.9598 31.9598 26.6052 31.9598 20C31.9598 13.3948 26.6052 8.04016 20 8.04016C13.3948 8.04016 8.04016 13.3948 8.04016 20C8.04016 26.6052 13.3948 31.9598 20 31.9598Z" fill="#83D9FF"/>
|
||||
<path d="M20 39.9999V31.9598C21.5268 31.9598 22.9858 31.6741 24.3283 31.1526L27.0792 38.7106C24.8779 39.5437 22.4927 39.9999 20 39.9999Z" fill="#3FEFEF"/>
|
||||
<path d="M24.3287 31.1526C25.7106 30.6158 26.9685 29.8294 28.047 28.8483L33.2182 35.0101C31.4274 36.5875 29.3525 37.8503 27.0796 38.7106L24.3287 31.1526Z" fill="#1DD1D9"/>
|
||||
<path d="M28.0469 28.8483C29.1141 27.877 30.0052 26.7155 30.6665 25.4166L37.6355 29.4407C36.5033 31.5525 35.0015 33.4382 33.2178 35.0101L28.0469 28.8483Z" fill="#17B5BA"/>
|
||||
<path d="M31.6322 17.2079L39.5598 15.8099C39.8488 17.1613 40.0001 18.5626 40.0001 20C40.0001 20.9335 39.9357 21.8518 39.8118 22.7518L31.8843 21.3547C31.934 20.9103 31.96 20.4581 31.96 20C31.96 19.0381 31.8464 18.1039 31.6322 17.2079Z" fill="#9BE058"/>
|
||||
<path d="M30.0234 13.472L36.993 9.448C38.1915 11.3749 39.0719 13.5197 39.5596 15.81L31.632 17.208C31.3094 15.8591 30.7589 14.5997 30.0234 13.472Z" fill="#C0FF66"/>
|
||||
<path d="M27.317 10.5393L32.4882 4.37659C34.2619 5.79626 35.7887 7.51166 36.9935 9.448L30.0239 13.472C29.2906 12.3493 28.3738 11.3578 27.317 10.5393Z" fill="#FFDF46"/>
|
||||
<path d="M13.3973 1.11633C15.4649 0.392761 17.6863 0 20.0001 0V8.04016C18.6519 8.04016 17.3564 8.26324 16.1473 8.67432L13.3973 1.11633Z" fill="#FC3E81"/>
|
||||
<path d="M7.51233 4.37653C9.25824 2.97943 11.2434 1.8689 13.3964 1.11633H13.3973L16.1473 8.67432C14.8845 9.10339 13.7169 9.73847 12.6835 10.5392L7.51233 4.37653Z" fill="#F01054"/>
|
||||
<path d="M3.0072 9.448C4.21204 7.51166 5.73883 5.79657 7.51251 4.37659L12.6837 10.5393C11.6269 11.3578 10.7101 12.3493 9.97711 13.472L3.0072 9.448Z" fill="#7884EA"/>
|
||||
<path d="M0.18811 22.7517L8.11566 21.3546C8.27924 22.8024 8.70068 24.1723 9.33362 25.4165L2.36432 29.4406C1.26813 27.3971 0.51648 25.1418 0.18811 22.7517Z" fill="#1685FB"/>
|
||||
<path d="M2.36438 29.4407L9.33337 25.4166C9.995 26.7155 10.8861 27.877 11.9533 28.8483L6.7821 35.0101C4.99866 33.4382 3.49689 31.5525 2.36438 29.4407Z" fill="#43A3F9"/>
|
||||
<path d="M6.78235 35.0101L11.9536 28.8483C13.0317 29.8294 14.2897 30.6158 15.6718 31.1526L12.9207 38.7106C10.648 37.8503 8.57312 36.5875 6.78235 35.0101Z" fill="#64BDFF"/>
|
||||
<path d="M0.440796 15.81C0.928467 13.5197 1.8089 11.3749 3.00732 9.448L9.97693 13.472C9.24146 14.5997 8.69092 15.8591 8.36835 17.208L0.440796 15.81Z" fill="#4A5BE5"/>
|
||||
<path d="M30.6663 25.4165C31.2989 24.172 31.7203 22.8024 31.8839 21.3546L39.8115 22.7517C39.4831 25.1418 38.7314 27.3971 37.6353 29.4406L30.6663 25.4165Z" fill="#1CC939"/>
|
||||
<path d="M0 20C0 18.5626 0.151367 17.1613 0.440369 15.8099L8.36792 17.2079C8.15369 18.1039 8.04016 19.0381 8.04016 20C8.04016 20.4581 8.0661 20.9103 8.11584 21.3547L0.188293 22.7518C0.0643921 21.8518 0 20.9335 0 20Z" fill="#364EC6"/>
|
||||
<path d="M23.8527 8.67432L26.6035 1.11633C28.7565 1.8689 30.742 2.97943 32.4876 4.37683L27.3167 10.5392C26.2831 9.73847 25.1152 9.10339 23.8527 8.67432Z" fill="#F9B200"/>
|
||||
<path d="M20 8.04016V0C22.3138 0 24.5361 0.392761 26.6037 1.11633L23.8525 8.67432C22.6437 8.26324 21.3483 8.04016 20 8.04016Z" fill="#FD6096"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 3.3 KiB |
@@ -0,0 +1,20 @@
|
||||
<svg width="40" height="40" viewBox="0 0 40 40" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<path d="M0 20C0 8.95416 8.95416 0 20 0C31.0458 0 40 8.95416 40 20C40 31.0458 31.0458 40 20 40C8.95416 40 0 31.0458 0 20ZM20 31.9598C26.6052 31.9598 31.9598 26.6052 31.9598 20C31.9598 13.3948 26.6052 8.04016 20 8.04016C13.3948 8.04016 8.04016 13.3948 8.04016 20C8.04016 26.6052 13.3948 31.9598 20 31.9598Z" fill="#F2F2F2"/>
|
||||
<path d="M20 39.9999V31.9598C21.5268 31.9598 22.9858 31.6741 24.3283 31.1526L27.0792 38.7106C24.8779 39.5437 22.4927 39.9999 20 39.9999Z" fill="#FCFAE0"/>
|
||||
<path d="M24.3287 31.1526C25.7106 30.6158 26.9685 29.8294 28.047 28.8483L33.2182 35.0101C31.4274 36.5875 29.3525 37.8503 27.0796 38.7106L24.3287 31.1526Z" fill="#FCFAE0"/>
|
||||
<path d="M28.0469 28.8483C29.1141 27.877 30.0052 26.7155 30.6665 25.4166L37.6355 29.4407C36.5033 31.5525 35.0015 33.4382 33.2178 35.0101L28.0469 28.8483Z" fill="#FCFAE0"/>
|
||||
<path d="M31.6322 17.2079L39.5598 15.8099C39.8488 17.1613 40.0001 18.5626 40.0001 20C40.0001 20.9335 39.9357 21.8518 39.8118 22.7518L31.8843 21.3547C31.934 20.9103 31.96 20.4581 31.96 20C31.96 19.0381 31.8464 18.1039 31.6322 17.2079Z" fill="#FAE63A"/>
|
||||
<path d="M30.0234 13.472L36.993 9.448C38.1915 11.3749 39.0719 13.5197 39.5596 15.81L31.632 17.208C31.3094 15.8591 30.7589 14.5997 30.0234 13.472Z" fill="#FAE63A"/>
|
||||
<path d="M27.317 10.5393L32.4882 4.37659C34.2619 5.79626 35.7887 7.51166 36.9935 9.448L30.0239 13.472C29.2906 12.3493 28.3738 11.3578 27.317 10.5393Z" fill="#FDC242"/>
|
||||
<path d="M13.3973 1.11633C15.4649 0.392761 17.6863 0 20.0001 0V8.04016C18.6519 8.04016 17.3564 8.26324 16.1473 8.67432L13.3973 1.11633Z" fill="#7FE1FE"/>
|
||||
<path d="M7.51233 4.37653C9.25824 2.97943 11.2434 1.8689 13.3964 1.11633H13.3973L16.1473 8.67432C14.8845 9.10339 13.7169 9.73847 12.6835 10.5392L7.51233 4.37653Z" fill="#7FE1FE"/>
|
||||
<path d="M3.0072 9.448C4.21204 7.51166 5.73883 5.79657 7.51251 4.37659L12.6837 10.5393C11.6269 11.3578 10.7101 12.3493 9.97711 13.472L3.0072 9.448Z" fill="#7FE1FE"/>
|
||||
<path d="M0.18811 22.7517L8.11566 21.3546C8.27924 22.8024 8.70068 24.1723 9.33362 25.4165L2.36432 29.4406C1.26813 27.3971 0.51648 25.1418 0.18811 22.7517Z" fill="#CBF1FA"/>
|
||||
<path d="M2.36438 29.4407L9.33337 25.4166C9.995 26.7155 10.8861 27.877 11.9533 28.8483L6.7821 35.0101C4.99866 33.4382 3.49689 31.5525 2.36438 29.4407Z" fill="#F2F2F2"/>
|
||||
<path d="M6.78235 35.0101L11.9536 28.8483C13.0317 29.8294 14.2897 30.6158 15.6718 31.1526L12.9207 38.7106C10.648 37.8503 8.57312 36.5875 6.78235 35.0101Z" fill="#F2F2F2"/>
|
||||
<path d="M0.440796 15.81C0.928467 13.5197 1.8089 11.3749 3.00732 9.448L9.97693 13.472C9.24146 14.5997 8.69092 15.8591 8.36835 17.208L0.440796 15.81Z" fill="#CBF1FA"/>
|
||||
<path d="M30.6663 25.4165C31.2989 24.172 31.7203 22.8024 31.8839 21.3546L39.8115 22.7517C39.4831 25.1418 38.7314 27.3971 37.6353 29.4406L30.6663 25.4165Z" fill="#FAE63A"/>
|
||||
<path d="M0 20C0 18.5626 0.151367 17.1613 0.440369 15.8099L8.36792 17.2079C8.15369 18.1039 8.04016 19.0381 8.04016 20C8.04016 20.4581 8.0661 20.9103 8.11584 21.3547L0.188293 22.7518C0.0643921 21.8518 0 20.9335 0 20Z" fill="#CBF1FA"/>
|
||||
<path d="M23.8527 8.67432L26.6035 1.11633C28.7565 1.8689 30.742 2.97943 32.4876 4.37683L27.3167 10.5392C26.2831 9.73847 25.1152 9.10339 23.8527 8.67432Z" fill="#FDC242"/>
|
||||
<path d="M20 8.04016V0C22.3138 0 24.5361 0.392761 26.6037 1.11633L23.8525 8.67432C22.6437 8.26324 21.3483 8.04016 20 8.04016Z" fill="#FDC242"/>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 3.3 KiB |
@@ -23,7 +23,7 @@ class AppLayout extends StatelessWidget {
|
||||
child: Scaffold(
|
||||
backgroundColor: ColorsManager.backgroundColor,
|
||||
extendBodyBehindAppBar: true,
|
||||
// extendBody: true,
|
||||
extendBody: true,
|
||||
appBar: DefaultAppBar(),
|
||||
body: AppBody(),
|
||||
bottomNavigationBar: DefaultNavBar(),
|
||||
|
||||
@@ -26,7 +26,8 @@ class AppBody extends StatelessWidget {
|
||||
),
|
||||
),
|
||||
child: Padding(
|
||||
padding: const EdgeInsets.only(top: 60, right: 15, left: 15),
|
||||
padding:
|
||||
const EdgeInsets.only(top: 60, right: 15, left: 15, bottom: 80),
|
||||
child: NavCubit.of(context).currentPage,
|
||||
),
|
||||
);
|
||||
|
||||
@@ -21,7 +21,7 @@ class DefaultNavBar extends StatelessWidget {
|
||||
onTap: (int index) {
|
||||
cubit.updatePageIndex(index, context);
|
||||
if (DevicesCubit.get(context).chosenCategoryView != null) {
|
||||
Navigator.pop(context);
|
||||
DevicesCubit().clearCategoriesSelection(context);
|
||||
}
|
||||
},
|
||||
currentIndex: cubit.getPageIndex,
|
||||
|
||||
@@ -11,11 +11,6 @@ class AcCubit extends Cubit<AcState> {
|
||||
|
||||
static AcCubit get(context) => BlocProvider.of(context);
|
||||
|
||||
void selectAC(ACModel model) {
|
||||
model.isSelected = !model.isSelected;
|
||||
emit(ACSelected());
|
||||
}
|
||||
|
||||
ACModel? getSelectedAC() {
|
||||
for (var ac in DevicesCubit.categories[0].devices) {
|
||||
if (ac is ACModel && ac.isSelected) {
|
||||
@@ -36,7 +31,9 @@ class AcCubit extends Cubit<AcState> {
|
||||
}
|
||||
|
||||
void setACTemp(ACModel model, double temp) {
|
||||
model.temperature = temp;
|
||||
if (model.bounds.min <= temp && temp <= model.bounds.max) {
|
||||
model.temperature = temp;
|
||||
}
|
||||
emit(ACsTempChanged(temp));
|
||||
}
|
||||
|
||||
|
||||
@@ -35,6 +35,10 @@ class DevicesCubit extends Cubit<DevicesState> {
|
||||
location: '',
|
||||
image: '',
|
||||
timer: null,
|
||||
bounds: Bounds(
|
||||
min: 20,
|
||||
max: 30,
|
||||
),
|
||||
),
|
||||
ACModel(
|
||||
name: "Master Bedroom AC",
|
||||
@@ -48,6 +52,10 @@ class DevicesCubit extends Cubit<DevicesState> {
|
||||
location: '',
|
||||
image: '',
|
||||
timer: null,
|
||||
bounds: Bounds(
|
||||
min: 20,
|
||||
max: 30,
|
||||
),
|
||||
),
|
||||
ACModel(
|
||||
name: "Kitchen AC",
|
||||
@@ -61,6 +69,10 @@ class DevicesCubit extends Cubit<DevicesState> {
|
||||
location: '',
|
||||
image: '',
|
||||
timer: null,
|
||||
bounds: Bounds(
|
||||
min: 20,
|
||||
max: 30,
|
||||
),
|
||||
),
|
||||
ACModel(
|
||||
name: "Bathroom AC",
|
||||
@@ -74,6 +86,10 @@ class DevicesCubit extends Cubit<DevicesState> {
|
||||
location: '',
|
||||
image: '',
|
||||
timer: null,
|
||||
bounds: Bounds(
|
||||
min: 20,
|
||||
max: 30,
|
||||
),
|
||||
),
|
||||
],
|
||||
icon: Assets.iconsAC,
|
||||
@@ -94,6 +110,12 @@ class DevicesCubit extends Cubit<DevicesState> {
|
||||
type: '',
|
||||
location: '',
|
||||
image: '',
|
||||
recentColors: [
|
||||
0xFF83D9FF,
|
||||
0xFFFC3E81,
|
||||
0xFFC0FF66,
|
||||
0xFFFDC242,
|
||||
],
|
||||
),
|
||||
LightModel(
|
||||
name: "Master Bedroom Light",
|
||||
@@ -106,6 +128,12 @@ class DevicesCubit extends Cubit<DevicesState> {
|
||||
type: '',
|
||||
location: '',
|
||||
image: '',
|
||||
recentColors: [
|
||||
0xFF83D9FF,
|
||||
0xFFFC3E81,
|
||||
0xFFC0FF66,
|
||||
0xFFFDC242,
|
||||
],
|
||||
),
|
||||
LightModel(
|
||||
name: "Kitchen Light",
|
||||
@@ -118,6 +146,12 @@ class DevicesCubit extends Cubit<DevicesState> {
|
||||
type: '',
|
||||
location: '',
|
||||
image: '',
|
||||
recentColors: [
|
||||
0xFF83D9FF,
|
||||
0xFFFC3E81,
|
||||
0xFFC0FF66,
|
||||
0xFFFDC242,
|
||||
],
|
||||
),
|
||||
LightModel(
|
||||
name: "Bathroom Light",
|
||||
@@ -130,6 +164,12 @@ class DevicesCubit extends Cubit<DevicesState> {
|
||||
type: '',
|
||||
location: '',
|
||||
image: '',
|
||||
recentColors: [
|
||||
0xFF83D9FF,
|
||||
0xFFFC3E81,
|
||||
0xFFC0FF66,
|
||||
0xFFFDC242,
|
||||
],
|
||||
),
|
||||
LightModel(
|
||||
name: "Balcony Light",
|
||||
@@ -142,6 +182,12 @@ class DevicesCubit extends Cubit<DevicesState> {
|
||||
type: '',
|
||||
location: '',
|
||||
image: '',
|
||||
recentColors: [
|
||||
0xFF83D9FF,
|
||||
0xFFFC3E81,
|
||||
0xFFC0FF66,
|
||||
0xFFFDC242,
|
||||
],
|
||||
),
|
||||
],
|
||||
icon: Assets.iconsLight,
|
||||
@@ -179,6 +225,24 @@ class DevicesCubit extends Cubit<DevicesState> {
|
||||
),
|
||||
];
|
||||
|
||||
selectCategory(int index) {
|
||||
for (var i = 0; i < categories.length; i++) {
|
||||
if (i == index) {
|
||||
categories[i].isSelected = true;
|
||||
} else {
|
||||
categories[i].isSelected = false;
|
||||
}
|
||||
}
|
||||
emit(DevicesCategoryChanged());
|
||||
}
|
||||
|
||||
unselectAllCategories() {
|
||||
for (var category in categories) {
|
||||
category.isSelected = false;
|
||||
}
|
||||
emit(DevicesCategoryChanged());
|
||||
}
|
||||
|
||||
Widget? get chosenCategoryView {
|
||||
for (var category in categories) {
|
||||
if (category.isSelected) {
|
||||
@@ -188,7 +252,32 @@ class DevicesCubit extends Cubit<DevicesState> {
|
||||
return null;
|
||||
}
|
||||
|
||||
void changeCategorySwitchValue(DevicesCategoryModel category) {
|
||||
selectDevice(DeviceModel device) {
|
||||
for (var category in categories) {
|
||||
for (var device in category.devices) {
|
||||
if (device.isSelected) {
|
||||
category.isSelected = false;
|
||||
emit(DeviceSelected());
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
device.isSelected = !device.isSelected;
|
||||
emit(DeviceSelected());
|
||||
}
|
||||
|
||||
DeviceModel? getSelectedDevice() {
|
||||
for (var category in categories) {
|
||||
for (var device in category.devices) {
|
||||
if (device.isSelected) {
|
||||
return device;
|
||||
}
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
changeCategorySwitchValue(DevicesCategoryModel category) {
|
||||
if (category.devicesStatus != null) {
|
||||
category.devicesStatus = !category.devicesStatus!;
|
||||
for (var device in category.devices) {
|
||||
@@ -200,11 +289,12 @@ class DevicesCubit extends Cubit<DevicesState> {
|
||||
device.status = true;
|
||||
}
|
||||
}
|
||||
updateDevicesStatus(category);
|
||||
|
||||
emit(CategorySwitchChanged());
|
||||
}
|
||||
|
||||
void turnOnOffDevice(DeviceModel device) {
|
||||
turnOnOffDevice(DeviceModel device) {
|
||||
device.status = !device.status!;
|
||||
DevicesCategoryModel category =
|
||||
categories.firstWhere((category) => category.devices.contains(device));
|
||||
@@ -212,7 +302,7 @@ class DevicesCubit extends Cubit<DevicesState> {
|
||||
emit(DeviceSwitchChanged());
|
||||
}
|
||||
|
||||
void updateDevicesStatus(DevicesCategoryModel category) {
|
||||
updateDevicesStatus(DevicesCategoryModel category) {
|
||||
bool? tempStatus = category.devices[0].status;
|
||||
for (var ac in category.devices) {
|
||||
//check if there any ac have a different status than the initial ==> turn off the universal switch
|
||||
@@ -226,23 +316,25 @@ class DevicesCubit extends Cubit<DevicesState> {
|
||||
}
|
||||
}
|
||||
|
||||
void turnAllDevicesOff(DevicesCategoryModel category) {
|
||||
turnAllDevicesOff(DevicesCategoryModel category) {
|
||||
for (var device in category.devices) {
|
||||
device.status = false;
|
||||
}
|
||||
changeCategorySwitchValue(category);
|
||||
updateDevicesStatus(category);
|
||||
emit(CategorySwitchChanged());
|
||||
}
|
||||
|
||||
void turnAllDevicesOn(DevicesCategoryModel category) {
|
||||
turnAllDevicesOn(DevicesCategoryModel category) {
|
||||
for (var device in category.devices) {
|
||||
device.status = true;
|
||||
}
|
||||
changeCategorySwitchValue(category);
|
||||
updateDevicesStatus(category);
|
||||
emit(CategorySwitchChanged());
|
||||
}
|
||||
|
||||
void areAllDevicesOff(DevicesCategoryModel category) {
|
||||
areAllDevicesOff(DevicesCategoryModel category) {
|
||||
for (var device in category.devices) {
|
||||
if (device.status ?? false) {
|
||||
category.devicesStatus = false;
|
||||
@@ -252,23 +344,15 @@ class DevicesCubit extends Cubit<DevicesState> {
|
||||
}
|
||||
}
|
||||
|
||||
void selectCategory(int index) {
|
||||
for (var i = 0; i < categories.length; i++) {
|
||||
if (i == index) {
|
||||
categories[i].isSelected = true;
|
||||
} else {
|
||||
categories[i].isSelected = false;
|
||||
}
|
||||
}
|
||||
emit(DevicesCategoryChanged());
|
||||
}
|
||||
|
||||
static void clearCategoriesSelection() {
|
||||
clearCategoriesSelection(BuildContext context) {
|
||||
for (var category in categories) {
|
||||
category.isSelected = false;
|
||||
for (var device in category.devices) {
|
||||
device.isSelected = false;
|
||||
}
|
||||
}
|
||||
Navigator.popUntil(context, (route) => route.isFirst);
|
||||
|
||||
emit(DevicesCategoryChanged());
|
||||
}
|
||||
}
|
||||
|
||||
@@ -18,3 +18,5 @@ class DevicesCategoryChanged extends DevicesState {}
|
||||
class CategorySwitchChanged extends DevicesState {}
|
||||
|
||||
class DeviceSwitchChanged extends DevicesState {}
|
||||
|
||||
class DeviceSelected extends DevicesState {}
|
||||
|
||||
@@ -8,6 +8,29 @@ class LightsCubit extends Cubit<LightsState> {
|
||||
|
||||
static LightsCubit get(context) => BlocProvider.of(context);
|
||||
|
||||
Map<int, LightMode> lightModes = {
|
||||
0: LightMode.Doze,
|
||||
1: LightMode.Relax,
|
||||
2: LightMode.Reading,
|
||||
3: LightMode.Energizing,
|
||||
};
|
||||
|
||||
setLightingMode(LightModel light, LightMode mode) {
|
||||
light.lightingMode =
|
||||
lightModes.entries.firstWhere((element) => element.value == mode).key;
|
||||
emit(LightModeChanged(mode));
|
||||
}
|
||||
|
||||
toggleLight(LightModel light) {
|
||||
light.status != null ? light.status = !light.status! : light.status = true;
|
||||
emit(LightToggled(light));
|
||||
}
|
||||
|
||||
setColor(LightModel light, int color) {
|
||||
light.color = color;
|
||||
emit(LightColorChanged(color));
|
||||
}
|
||||
|
||||
int getBrightness(LightModel light) {
|
||||
return light.brightness.toInt();
|
||||
}
|
||||
@@ -30,3 +53,10 @@ class LightsCubit extends Cubit<LightsState> {
|
||||
setBrightness(light, newBrightness);
|
||||
}
|
||||
}
|
||||
|
||||
enum LightMode {
|
||||
Doze,
|
||||
Relax,
|
||||
Reading,
|
||||
Energizing,
|
||||
}
|
||||
|
||||
@@ -19,3 +19,21 @@ class LightBrightnessChanged extends LightsState {
|
||||
|
||||
LightBrightnessChanged(this.brightness);
|
||||
}
|
||||
|
||||
class LightToggled extends LightsState {
|
||||
final LightModel light;
|
||||
|
||||
LightToggled(this.light);
|
||||
}
|
||||
|
||||
class LightColorChanged extends LightsState {
|
||||
final int color;
|
||||
|
||||
LightColorChanged(this.color);
|
||||
}
|
||||
|
||||
class LightModeChanged extends LightsState {
|
||||
final LightMode mode;
|
||||
|
||||
LightModeChanged(this.mode);
|
||||
}
|
||||
|
||||
@@ -9,11 +9,14 @@ class ACModel extends DeviceModel {
|
||||
|
||||
late double coolTo;
|
||||
|
||||
late Bounds bounds;
|
||||
|
||||
ACModel({
|
||||
required this.temperature,
|
||||
required this.fanSpeed,
|
||||
required this.tempMode,
|
||||
required this.coolTo,
|
||||
required this.bounds,
|
||||
required super.id,
|
||||
required super.name,
|
||||
required super.type,
|
||||
@@ -51,6 +54,31 @@ class ACModel extends DeviceModel {
|
||||
image: json['image'],
|
||||
timer: json['timer'],
|
||||
coolTo: json['coolTo'],
|
||||
bounds: Bounds.fromJson(json['bounds']),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
class Bounds {
|
||||
late double min;
|
||||
late double max;
|
||||
|
||||
Bounds({
|
||||
required this.min,
|
||||
required this.max,
|
||||
});
|
||||
|
||||
Map<String, dynamic> toJson() {
|
||||
return {
|
||||
'min': min,
|
||||
'max': max,
|
||||
};
|
||||
}
|
||||
|
||||
factory Bounds.fromJson(Map<String, dynamic> json) {
|
||||
return Bounds(
|
||||
min: json['min'],
|
||||
max: json['max'],
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -6,10 +6,13 @@ class LightModel extends DeviceModel {
|
||||
|
||||
late int lightingMode;
|
||||
|
||||
late List<int> recentColors;
|
||||
|
||||
LightModel({
|
||||
required this.brightness,
|
||||
required this.color,
|
||||
required this.lightingMode,
|
||||
required this.recentColors,
|
||||
required super.id,
|
||||
required super.name,
|
||||
required super.type,
|
||||
@@ -25,6 +28,7 @@ class LightModel extends DeviceModel {
|
||||
'color': color,
|
||||
'lightingMode': lightingMode,
|
||||
'timer': timer,
|
||||
'recentColors': recentColors,
|
||||
'id': id,
|
||||
'name': name,
|
||||
'status': status,
|
||||
@@ -46,6 +50,7 @@ class LightModel extends DeviceModel {
|
||||
type: json['type'],
|
||||
location: json['location'],
|
||||
image: json['image'],
|
||||
recentColors: json['recentColors'],
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -11,7 +11,11 @@ class CategoriesView extends StatelessWidget {
|
||||
return BlocProvider(
|
||||
create: (context) => DevicesCubit(),
|
||||
child: BlocBuilder<DevicesCubit, DevicesState>(
|
||||
builder: (context, state) => const DevicesViewBody(),
|
||||
builder: (context, state) => Container(
|
||||
padding: const EdgeInsets.all(8),
|
||||
width: MediaQuery.sizeOf(context).width,
|
||||
height: MediaQuery.sizeOf(context).height,
|
||||
child: const DevicesViewBody()),
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:syncrow_app/features/devices/bloc/AC/ac_cubit.dart';
|
||||
import 'package:flutter_bloc/flutter_bloc.dart';
|
||||
import 'package:syncrow_app/features/devices/bloc/devices_cubit.dart';
|
||||
import 'package:syncrow_app/features/devices/model/device_category_model.dart';
|
||||
import 'package:syncrow_app/features/devices/view/widgets/ACs/ac_mode_control_unit.dart';
|
||||
@@ -19,78 +19,79 @@ class ACsList extends StatelessWidget {
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
DevicesCategoryModel category = DevicesCubit.categories[0];
|
||||
return SingleChildScrollView(
|
||||
child: Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.stretch,
|
||||
children: [
|
||||
// universal AC controller
|
||||
const SizedBox(height: 10),
|
||||
const BodySmall(text: "All ACs"),
|
||||
const SizedBox(height: 5),
|
||||
UniversalSwitch(
|
||||
category: category,
|
||||
),
|
||||
const SizedBox(height: 10),
|
||||
const UniversalACTemp(),
|
||||
const SizedBox(height: 10),
|
||||
return BlocBuilder<DevicesCubit, DevicesState>(
|
||||
builder: (context, state) {
|
||||
return SingleChildScrollView(
|
||||
child: Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.stretch,
|
||||
children: [
|
||||
// universal AC controller
|
||||
const SizedBox(height: 10),
|
||||
const BodySmall(text: "All ACs"),
|
||||
const SizedBox(height: 5),
|
||||
UniversalSwitch(
|
||||
category: category,
|
||||
),
|
||||
const SizedBox(height: 10),
|
||||
const UniversalACTemp(),
|
||||
const SizedBox(height: 10),
|
||||
|
||||
// other ACs controls
|
||||
ListView.builder(
|
||||
shrinkWrap: true,
|
||||
physics: const NeverScrollableScrollPhysics(),
|
||||
padding: const EdgeInsets.all(0),
|
||||
itemCount: category.devices.length,
|
||||
itemBuilder: (context, index) {
|
||||
ACModel ac = category.devices[index] as ACModel;
|
||||
return Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Row(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
||||
crossAxisAlignment: CrossAxisAlignment.end,
|
||||
// other ACs controls
|
||||
ListView.builder(
|
||||
shrinkWrap: true,
|
||||
physics: const NeverScrollableScrollPhysics(),
|
||||
padding: const EdgeInsets.all(0),
|
||||
itemCount: category.devices.length,
|
||||
itemBuilder: (context, index) {
|
||||
ACModel ac = category.devices[index] as ACModel;
|
||||
return Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
BodySmall(text: category.devices[index].name ?? ""),
|
||||
IconButton(
|
||||
onPressed: () {
|
||||
var device = category.devices[index];
|
||||
if (device is ACModel) {
|
||||
AcCubit.get(context).selectAC(device);
|
||||
}
|
||||
},
|
||||
icon: const Icon(
|
||||
Icons.arrow_forward_ios,
|
||||
),
|
||||
style: ButtonStyle(
|
||||
padding: MaterialStateProperty.all(
|
||||
const EdgeInsets.all(0),
|
||||
Row(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
||||
crossAxisAlignment: CrossAxisAlignment.end,
|
||||
children: [
|
||||
BodySmall(text: category.devices[index].name ?? ""),
|
||||
IconButton(
|
||||
onPressed: () {
|
||||
DevicesCubit.get(context).selectDevice(ac);
|
||||
},
|
||||
icon: const Icon(
|
||||
Icons.arrow_forward_ios,
|
||||
),
|
||||
style: ButtonStyle(
|
||||
padding: MaterialStateProperty.all(
|
||||
const EdgeInsets.all(0),
|
||||
),
|
||||
iconSize: MaterialStateProperty.all(15),
|
||||
alignment: Alignment.bottomRight,
|
||||
),
|
||||
),
|
||||
iconSize: MaterialStateProperty.all(15),
|
||||
alignment: Alignment.bottomRight,
|
||||
),
|
||||
],
|
||||
),
|
||||
const SizedBox(height: 5),
|
||||
if (category.devices[index] is ACModel)
|
||||
DevicesDefaultSwitch(
|
||||
model: ac,
|
||||
),
|
||||
const SizedBox(height: 10),
|
||||
ACTempWidget(
|
||||
ac,
|
||||
),
|
||||
const SizedBox(height: 10),
|
||||
if (category.devices[index] is ACModel)
|
||||
ACModeControlUnit(
|
||||
model: ac,
|
||||
),
|
||||
const SizedBox(height: 10),
|
||||
],
|
||||
),
|
||||
const SizedBox(height: 5),
|
||||
if (category.devices[index] is ACModel)
|
||||
DevicesDefaultSwitch(
|
||||
model: ac,
|
||||
),
|
||||
const SizedBox(height: 10),
|
||||
ACTempWidget(
|
||||
ac,
|
||||
),
|
||||
const SizedBox(height: 10),
|
||||
if (category.devices[index] is ACModel)
|
||||
ACModeControlUnit(
|
||||
model: ac,
|
||||
),
|
||||
const SizedBox(height: 10),
|
||||
],
|
||||
);
|
||||
},
|
||||
);
|
||||
},
|
||||
),
|
||||
],
|
||||
),
|
||||
],
|
||||
),
|
||||
);
|
||||
},
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -4,6 +4,7 @@ import 'package:flutter_bloc/flutter_bloc.dart';
|
||||
import 'package:syncrow_app/features/app_layout/view/widgets/default_app_bar.dart';
|
||||
import 'package:syncrow_app/features/app_layout/view/widgets/default_nav_bar.dart';
|
||||
import 'package:syncrow_app/features/devices/bloc/AC/ac_cubit.dart';
|
||||
import 'package:syncrow_app/features/devices/bloc/devices_cubit.dart';
|
||||
import 'package:syncrow_app/features/devices/model/ac_model.dart';
|
||||
import 'package:syncrow_app/features/devices/view/widgets/ACs/ac_interface.dart';
|
||||
import 'package:syncrow_app/features/devices/view/widgets/ACs/acs_list.dart';
|
||||
@@ -18,45 +19,53 @@ class ACsView extends StatelessWidget {
|
||||
Widget build(BuildContext context) {
|
||||
return BlocProvider(
|
||||
create: (context) => AcCubit(),
|
||||
child: BlocBuilder<AcCubit, AcState>(
|
||||
child: BlocBuilder<DevicesCubit, DevicesState>(
|
||||
builder: (context, state) {
|
||||
ACModel? selectedAC = AcCubit.get(context).getSelectedAC();
|
||||
return AnnotatedRegion(
|
||||
value: SystemUiOverlayStyle(
|
||||
statusBarColor: ColorsManager.primaryColor.withOpacity(0.5),
|
||||
statusBarIconBrightness: Brightness.light,
|
||||
),
|
||||
child: SafeArea(
|
||||
child: Scaffold(
|
||||
backgroundColor: ColorsManager.backgroundColor,
|
||||
extendBodyBehindAppBar: true,
|
||||
extendBody: true,
|
||||
appBar: const DefaultAppBar(),
|
||||
body: Container(
|
||||
width: MediaQuery.sizeOf(context).width,
|
||||
height: MediaQuery.sizeOf(context).height,
|
||||
decoration: const BoxDecoration(
|
||||
image: DecorationImage(
|
||||
image: AssetImage(
|
||||
Assets.imagesBackground,
|
||||
return BlocBuilder<AcCubit, AcState>(
|
||||
builder: (context, state) {
|
||||
ACModel? selectedAC;
|
||||
if (DevicesCubit.get(context).getSelectedDevice() is ACModel) {
|
||||
selectedAC =
|
||||
DevicesCubit.get(context).getSelectedDevice() as ACModel;
|
||||
}
|
||||
return AnnotatedRegion(
|
||||
value: SystemUiOverlayStyle(
|
||||
statusBarColor: ColorsManager.primaryColor.withOpacity(0.5),
|
||||
statusBarIconBrightness: Brightness.light,
|
||||
),
|
||||
child: SafeArea(
|
||||
child: Scaffold(
|
||||
backgroundColor: ColorsManager.backgroundColor,
|
||||
extendBodyBehindAppBar: true,
|
||||
extendBody: true,
|
||||
appBar: const DefaultAppBar(),
|
||||
body: Container(
|
||||
width: MediaQuery.sizeOf(context).width,
|
||||
height: MediaQuery.sizeOf(context).height,
|
||||
decoration: const BoxDecoration(
|
||||
image: DecorationImage(
|
||||
image: AssetImage(
|
||||
Assets.imagesBackground,
|
||||
),
|
||||
fit: BoxFit.cover,
|
||||
opacity: 0.4,
|
||||
),
|
||||
),
|
||||
child: Padding(
|
||||
padding: const EdgeInsets.only(
|
||||
top: 60, right: 15, left: 15, bottom: 80),
|
||||
child: SizedBox.expand(
|
||||
child: selectedAC != null
|
||||
? AcInterface(acModel: selectedAC)
|
||||
: const ACsList(),
|
||||
),
|
||||
),
|
||||
fit: BoxFit.cover,
|
||||
opacity: 0.4,
|
||||
),
|
||||
),
|
||||
child: Padding(
|
||||
padding: const EdgeInsets.only(
|
||||
top: 60, right: 15, left: 15, bottom: 80),
|
||||
child: SizedBox.expand(
|
||||
child: selectedAC != null
|
||||
? AcInterface(acModel: selectedAC)
|
||||
: const ACsList(),
|
||||
),
|
||||
bottomNavigationBar: const DefaultNavBar(),
|
||||
),
|
||||
),
|
||||
bottomNavigationBar: const DefaultNavBar(),
|
||||
),
|
||||
),
|
||||
);
|
||||
},
|
||||
);
|
||||
},
|
||||
),
|
||||
|
||||
@@ -1,4 +1,6 @@
|
||||
import 'package:flutter/cupertino.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter/widgets.dart';
|
||||
import 'package:syncrow_app/features/devices/view/widgets/devices_mode_tab.dart';
|
||||
import 'package:syncrow_app/features/devices/view/widgets/switches.dart';
|
||||
import 'package:syncrow_app/features/shared_widgets/text_widgets/title_medium.dart';
|
||||
@@ -11,10 +13,11 @@ class DevicesCategoriesView extends StatelessWidget {
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Column(
|
||||
return const Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
Expanded(
|
||||
flex: 3,
|
||||
child: Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
@@ -30,7 +33,7 @@ class DevicesCategoriesView extends StatelessWidget {
|
||||
),
|
||||
),
|
||||
Expanded(
|
||||
flex: 3,
|
||||
flex: 11,
|
||||
child: SingleChildScrollView(
|
||||
child: Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
|
||||
@@ -19,14 +19,14 @@ class DevicesViewBody extends StatelessWidget {
|
||||
create: (context) => DevicesCubit(),
|
||||
child: BlocBuilder<DevicesCubit, DevicesState>(
|
||||
builder: (context, state) {
|
||||
//TODO : move to NavigationCubit
|
||||
PageController pageController = PageController();
|
||||
return state is DevicesLoading
|
||||
? const Center(child: CircularProgressIndicator())
|
||||
: Column(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
||||
children: [
|
||||
SizedBox(
|
||||
width: MediaQuery.sizeOf(context).width,
|
||||
height: MediaQuery.sizeOf(context).height - 252,
|
||||
Expanded(
|
||||
child: PageView(
|
||||
controller: pageController,
|
||||
children: const [
|
||||
@@ -111,7 +111,17 @@ class DevicesViewBody extends StatelessWidget {
|
||||
SmoothPageIndicator(
|
||||
controller: pageController,
|
||||
count: 3,
|
||||
effect: const WormEffect()),
|
||||
effect: const WormEffect(
|
||||
dotHeight: 8,
|
||||
dotWidth: 8,
|
||||
),
|
||||
onDotClicked: (index) {
|
||||
pageController.animateToPage(
|
||||
index,
|
||||
duration: const Duration(milliseconds: 300),
|
||||
curve: Curves.ease,
|
||||
);
|
||||
}),
|
||||
],
|
||||
);
|
||||
},
|
||||
|
||||
@@ -33,7 +33,7 @@ class LightBrightness extends StatelessWidget {
|
||||
),
|
||||
AnimatedPositioned(
|
||||
left: 0,
|
||||
duration: const Duration(milliseconds: 50),
|
||||
duration: const Duration(milliseconds: 0),
|
||||
child: Container(
|
||||
height: 60,
|
||||
width: (MediaQuery.of(context).size.width - 30) *
|
||||
|
||||
@@ -0,0 +1,34 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_bloc/flutter_bloc.dart';
|
||||
import 'package:syncrow_app/features/devices/bloc/lights/lights_cubit.dart';
|
||||
import 'package:syncrow_app/features/devices/model/light_model.dart';
|
||||
import 'package:syncrow_app/features/devices/view/widgets/lights/light_interface_contols.dart';
|
||||
import 'package:syncrow_app/features/devices/view/widgets/lights/light_interface_switch.dart';
|
||||
import 'package:syncrow_app/features/devices/view/widgets/lights/light_interface_timer.dart';
|
||||
|
||||
class LightInterface extends StatelessWidget {
|
||||
const LightInterface({super.key, required this.light});
|
||||
|
||||
final LightModel light;
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return BlocBuilder<LightsCubit, LightsState>(
|
||||
builder: (context, state) {
|
||||
return Padding(
|
||||
padding: const EdgeInsets.only(top: 70, right: 20, left: 20),
|
||||
child: SingleChildScrollView(
|
||||
child: Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.stretch,
|
||||
children: [
|
||||
LightInterfaceSwitch(light: light),
|
||||
LightInterfaceContols(light: light),
|
||||
const LightInterfaceTimer(),
|
||||
],
|
||||
),
|
||||
),
|
||||
);
|
||||
},
|
||||
);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,32 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:syncrow_app/features/devices/model/light_model.dart';
|
||||
import 'package:syncrow_app/features/devices/view/widgets/lights/light_interface_modes.dart';
|
||||
import 'package:syncrow_app/features/devices/view/widgets/lights/light_interface_recent_color.dart';
|
||||
import 'package:syncrow_app/features/devices/view/widgets/lights/light_interface_slider.dart';
|
||||
import 'package:syncrow_app/features/shared_widgets/default_container.dart';
|
||||
|
||||
class LightInterfaceContols extends StatelessWidget {
|
||||
const LightInterfaceContols({
|
||||
super.key,
|
||||
required this.light,
|
||||
});
|
||||
|
||||
final LightModel light;
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return DefaultContainer(
|
||||
boxConstraints: const BoxConstraints(maxHeight: 320),
|
||||
padding: const EdgeInsets.all(25),
|
||||
margin: const EdgeInsets.symmetric(vertical: 10),
|
||||
child: Column(
|
||||
mainAxisSize: MainAxisSize.min,
|
||||
children: [
|
||||
LightInterfaceSlider(light: light),
|
||||
LightInterfaceRecentColor(light: light),
|
||||
LightInterfaceModes(light: light)
|
||||
],
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,72 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:syncrow_app/features/devices/bloc/lights/lights_cubit.dart';
|
||||
import 'package:syncrow_app/features/devices/model/light_model.dart';
|
||||
import 'package:syncrow_app/features/shared_widgets/text_widgets/body_medium.dart';
|
||||
import 'package:syncrow_app/utils/context_extension.dart';
|
||||
import 'package:syncrow_app/utils/resource_manager/color_manager.dart';
|
||||
import 'package:syncrow_app/utils/resource_manager/strings_manager.dart';
|
||||
|
||||
class LightInterfaceModes extends StatelessWidget {
|
||||
const LightInterfaceModes({
|
||||
super.key,
|
||||
required this.light,
|
||||
});
|
||||
|
||||
final LightModel light;
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
BodyMedium(
|
||||
text: StringsManager.lightingModes,
|
||||
style: context.bodyMedium.copyWith(color: Colors.grey),
|
||||
),
|
||||
const SizedBox(height: 10),
|
||||
Wrap(
|
||||
spacing: 25,
|
||||
children: List.generate(
|
||||
LightsCubit.get(context).lightModes.length,
|
||||
(index) => InkWell(
|
||||
onTap: () => LightsCubit.get(context).setLightingMode(
|
||||
light, LightsCubit.get(context).lightModes[index]!),
|
||||
child: Column(
|
||||
children: [
|
||||
Container(
|
||||
width: 40,
|
||||
height: 40,
|
||||
decoration: ShapeDecoration(
|
||||
shape: const CircleBorder(),
|
||||
color: switch (index) {
|
||||
0 => ColorsManager.dozeColor,
|
||||
1 => ColorsManager.relaxColor,
|
||||
2 => ColorsManager.readingColor,
|
||||
3 => ColorsManager.energizingColor,
|
||||
_ => ColorsManager.primaryColor,
|
||||
},
|
||||
),
|
||||
),
|
||||
BodyMedium(
|
||||
text: switch (index) {
|
||||
0 => StringsManager.doze,
|
||||
1 => StringsManager.relax,
|
||||
2 => StringsManager.reading,
|
||||
3 => StringsManager.energizing,
|
||||
_ => "",
|
||||
},
|
||||
style: context.bodyMedium.copyWith(
|
||||
color: Colors.grey,
|
||||
fontSize: 10,
|
||||
),
|
||||
)
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
const SizedBox(height: 10)
|
||||
],
|
||||
);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,77 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_svg/flutter_svg.dart';
|
||||
import 'package:syncrow_app/features/devices/bloc/lights/lights_cubit.dart';
|
||||
import 'package:syncrow_app/features/devices/model/light_model.dart';
|
||||
import 'package:syncrow_app/utils/context_extension.dart';
|
||||
import 'package:syncrow_app/utils/resource_manager/color_manager.dart';
|
||||
|
||||
import '../../../../../generated/assets.dart';
|
||||
import '../../../../../utils/resource_manager/strings_manager.dart';
|
||||
import '../../../../shared_widgets/text_widgets/body_medium.dart';
|
||||
|
||||
class LightInterfaceRecentColor extends StatelessWidget {
|
||||
const LightInterfaceRecentColor({
|
||||
super.key,
|
||||
required this.light,
|
||||
});
|
||||
|
||||
final LightModel light;
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
BodyMedium(
|
||||
text: StringsManager.recentlyUsed,
|
||||
style: context.bodyMedium.copyWith(color: Colors.grey),
|
||||
),
|
||||
const SizedBox(height: 10),
|
||||
FittedBox(
|
||||
child: Row(
|
||||
children: [
|
||||
...List.generate(
|
||||
light.recentColors.length > 4 ? 4 : light.recentColors.length,
|
||||
(index) => InkWell(
|
||||
onTap: () {
|
||||
LightsCubit.get(context)
|
||||
.setColor(light, light.recentColors[index]);
|
||||
},
|
||||
child: Container(
|
||||
margin: const EdgeInsets.only(right: 10),
|
||||
width: 40,
|
||||
height: 40,
|
||||
decoration: ShapeDecoration(
|
||||
shape: const CircleBorder(),
|
||||
color: Color(light.recentColors[index]),
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
Container(
|
||||
margin: const EdgeInsets.only(right: 10),
|
||||
width: 1,
|
||||
height: 30,
|
||||
color: ColorsManager.greyColor,
|
||||
),
|
||||
SvgPicture.asset(
|
||||
Assets.iconsKalvin,
|
||||
height: 40,
|
||||
width: 40,
|
||||
),
|
||||
const SizedBox(
|
||||
width: 10,
|
||||
),
|
||||
SvgPicture.asset(
|
||||
Assets.iconsColorWheel,
|
||||
height: 40,
|
||||
width: 40,
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
const SizedBox(height: 10),
|
||||
],
|
||||
);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,74 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:syncrow_app/features/devices/bloc/lights/lights_cubit.dart';
|
||||
import 'package:syncrow_app/features/devices/model/light_model.dart';
|
||||
import 'package:syncrow_app/features/shared_widgets/text_widgets/body_medium.dart';
|
||||
import 'package:syncrow_app/features/shared_widgets/united_text.dart';
|
||||
import 'package:syncrow_app/utils/context_extension.dart';
|
||||
import 'package:syncrow_app/utils/resource_manager/color_manager.dart';
|
||||
import 'package:syncrow_app/utils/resource_manager/strings_manager.dart';
|
||||
|
||||
class LightInterfaceSlider extends StatelessWidget {
|
||||
const LightInterfaceSlider({
|
||||
super.key,
|
||||
required this.light,
|
||||
});
|
||||
|
||||
final LightModel light;
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.start,
|
||||
children: [
|
||||
BodyMedium(
|
||||
text: StringsManager.dimmerAndColor,
|
||||
style: context.bodyMedium.copyWith(color: Colors.grey),
|
||||
),
|
||||
Row(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
||||
children: [
|
||||
Expanded(
|
||||
child: UnitedText(
|
||||
value: light.brightness.toString(),
|
||||
unit: "%",
|
||||
valueStyle: context.bodyMedium.copyWith(
|
||||
color: Colors.grey,
|
||||
fontSize: 26,
|
||||
),
|
||||
unitStyle: context.bodyMedium.copyWith(
|
||||
color: Colors.grey,
|
||||
fontSize: 16,
|
||||
),
|
||||
),
|
||||
),
|
||||
Expanded(
|
||||
flex: 2,
|
||||
child: SliderTheme(
|
||||
data: SliderTheme.of(context).copyWith(
|
||||
thumbColor: ColorsManager.primaryColor,
|
||||
rangeThumbShape: const RoundRangeSliderThumbShape(
|
||||
enabledThumbRadius: 9,
|
||||
),
|
||||
thumbShape: const RoundSliderThumbShape(
|
||||
enabledThumbRadius: 9,
|
||||
),
|
||||
activeTrackColor: ColorsManager.greyColor,
|
||||
inactiveTrackColor: ColorsManager.greyColor,
|
||||
trackHeight: 5,
|
||||
),
|
||||
child: Slider(
|
||||
value: light.brightness,
|
||||
onChanged: (value) =>
|
||||
LightsCubit.get(context).setBrightness(light, value),
|
||||
min: 0,
|
||||
max: 100,
|
||||
),
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
const SizedBox(height: 10),
|
||||
],
|
||||
);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,69 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:syncrow_app/features/devices/bloc/lights/lights_cubit.dart';
|
||||
import 'package:syncrow_app/features/devices/model/light_model.dart';
|
||||
import 'package:syncrow_app/features/shared_widgets/text_widgets/body_large.dart';
|
||||
import 'package:syncrow_app/utils/context_extension.dart';
|
||||
import 'package:syncrow_app/utils/resource_manager/color_manager.dart';
|
||||
import 'package:syncrow_app/utils/resource_manager/strings_manager.dart';
|
||||
|
||||
import '../../../../shared_widgets/default_container.dart';
|
||||
|
||||
class LightInterfaceSwitch extends StatelessWidget {
|
||||
const LightInterfaceSwitch({
|
||||
super.key,
|
||||
required this.light,
|
||||
});
|
||||
|
||||
final LightModel light;
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return DefaultContainer(
|
||||
boxConstraints: const BoxConstraints(
|
||||
maxHeight: 65,
|
||||
),
|
||||
margin: const EdgeInsets.symmetric(vertical: 10),
|
||||
child: Padding(
|
||||
padding: const EdgeInsets.symmetric(horizontal: 15),
|
||||
child: Row(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceBetween,
|
||||
children: [
|
||||
BodyLarge(
|
||||
text: light.status ?? false
|
||||
? StringsManager.on
|
||||
: StringsManager.off,
|
||||
style:
|
||||
context.bodyLarge.copyWith(color: Colors.grey, fontSize: 24),
|
||||
),
|
||||
Container(
|
||||
width: 35,
|
||||
decoration: ShapeDecoration(
|
||||
color: light.status ?? false
|
||||
? ColorsManager.primaryWithOpacity
|
||||
: Colors.grey,
|
||||
shape: const CircleBorder(),
|
||||
),
|
||||
child: Center(
|
||||
child: IconButton(
|
||||
style: ButtonStyle(
|
||||
padding: MaterialStateProperty.all(
|
||||
const EdgeInsets.all(0),
|
||||
),
|
||||
iconSize: MaterialStateProperty.all(25),
|
||||
),
|
||||
onPressed: () {
|
||||
LightsCubit.get(context).toggleLight(light);
|
||||
},
|
||||
icon: const Icon(
|
||||
Icons.power_settings_new,
|
||||
color: Colors.white,
|
||||
),
|
||||
),
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,29 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:syncrow_app/features/shared_widgets/text_widgets/body_large.dart';
|
||||
import 'package:syncrow_app/utils/context_extension.dart';
|
||||
import 'package:syncrow_app/utils/resource_manager/strings_manager.dart';
|
||||
|
||||
import '../../../../shared_widgets/default_container.dart';
|
||||
|
||||
class LightInterfaceTimer extends StatelessWidget {
|
||||
const LightInterfaceTimer({
|
||||
super.key,
|
||||
});
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return DefaultContainer(
|
||||
boxConstraints: const BoxConstraints(maxHeight: 65, minHeight: 65),
|
||||
margin: const EdgeInsets.symmetric(vertical: 10),
|
||||
padding: const EdgeInsets.symmetric(horizontal: 35, vertical: 10),
|
||||
child: Row(
|
||||
children: [
|
||||
BodyLarge(
|
||||
text: StringsManager.timer,
|
||||
style: context.bodyLarge.copyWith(color: Colors.grey),
|
||||
),
|
||||
],
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
@@ -1,4 +1,5 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:syncrow_app/features/devices/bloc/devices_cubit.dart';
|
||||
import 'package:syncrow_app/features/devices/view/widgets/lights/light_brightness.dart';
|
||||
|
||||
import '../../../../shared_widgets/devices_default_switch.dart';
|
||||
@@ -31,7 +32,7 @@ class LightsList extends StatelessWidget {
|
||||
BodySmall(text: lights[index].name ?? ""),
|
||||
IconButton(
|
||||
onPressed: () {
|
||||
// LightsCubit.get(context).selectAC(device);
|
||||
DevicesCubit.get(context).selectDevice(lights[index]);
|
||||
},
|
||||
icon: const Icon(
|
||||
Icons.arrow_forward_ios,
|
||||
|
||||
@@ -1,17 +1,16 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter/services.dart';
|
||||
import 'package:flutter_bloc/flutter_bloc.dart';
|
||||
import 'package:syncrow_app/features/devices/view/widgets/lights/lights_list.dart';
|
||||
import 'package:syncrow_app/features/devices/view/widgets/lights/lights_view_list.dart';
|
||||
|
||||
import '../../../../../generated/assets.dart';
|
||||
import '../../../../../utils/resource_manager/color_manager.dart';
|
||||
import '../../../../app_layout/view/widgets/default_app_bar.dart';
|
||||
import '../../../../app_layout/view/widgets/default_nav_bar.dart';
|
||||
import '../../../../shared_widgets/text_widgets/body_small.dart';
|
||||
import '../../../bloc/devices_cubit.dart';
|
||||
import '../../../bloc/lights/lights_cubit.dart';
|
||||
import '../../../model/light_model.dart';
|
||||
import '../universal_switch.dart';
|
||||
import 'light_interface.dart';
|
||||
|
||||
class LightsView extends StatelessWidget {
|
||||
const LightsView({super.key});
|
||||
@@ -20,59 +19,53 @@ class LightsView extends StatelessWidget {
|
||||
Widget build(BuildContext context) {
|
||||
return BlocProvider(
|
||||
create: (context) => LightsCubit(),
|
||||
child: BlocBuilder<LightsCubit, LightsState>(
|
||||
child: BlocBuilder<DevicesCubit, DevicesState>(
|
||||
builder: (context, state) {
|
||||
List<LightModel> lights = [];
|
||||
for (var device in DevicesCubit.categories[1].devices) {
|
||||
if (device is LightModel) {
|
||||
lights.add(device);
|
||||
}
|
||||
}
|
||||
return AnnotatedRegion(
|
||||
value: SystemUiOverlayStyle(
|
||||
statusBarColor: ColorsManager.primaryColor.withOpacity(0.5),
|
||||
statusBarIconBrightness: Brightness.light,
|
||||
),
|
||||
child: SafeArea(
|
||||
child: Scaffold(
|
||||
backgroundColor: ColorsManager.backgroundColor,
|
||||
extendBodyBehindAppBar: true,
|
||||
extendBody: true,
|
||||
appBar: const DefaultAppBar(),
|
||||
body: Container(
|
||||
width: MediaQuery.sizeOf(context).width,
|
||||
height: MediaQuery.sizeOf(context).height,
|
||||
decoration: const BoxDecoration(
|
||||
image: DecorationImage(
|
||||
image: AssetImage(
|
||||
Assets.imagesBackground,
|
||||
),
|
||||
fit: BoxFit.cover,
|
||||
opacity: 0.4,
|
||||
),
|
||||
),
|
||||
child: Padding(
|
||||
padding: const EdgeInsets.only(
|
||||
top: 70, right: 15, left: 15, bottom: 80),
|
||||
child: SizedBox.expand(
|
||||
child: SingleChildScrollView(
|
||||
child: Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.stretch,
|
||||
children: [
|
||||
const BodySmall(text: "All Lights"),
|
||||
UniversalSwitch(
|
||||
category: DevicesCubit.categories[1],
|
||||
),
|
||||
LightsList(lights: lights),
|
||||
],
|
||||
return BlocBuilder<LightsCubit, LightsState>(
|
||||
builder: (context, state) {
|
||||
LightModel? selectedLight;
|
||||
if (DevicesCubit.get(context).getSelectedDevice() is LightModel) {
|
||||
selectedLight =
|
||||
DevicesCubit.get(context).getSelectedDevice() as LightModel;
|
||||
}
|
||||
List<LightModel> lights = [];
|
||||
for (var device in DevicesCubit.categories[1].devices) {
|
||||
if (device is LightModel) {
|
||||
lights.add(device);
|
||||
}
|
||||
}
|
||||
return AnnotatedRegion(
|
||||
value: SystemUiOverlayStyle(
|
||||
statusBarColor: ColorsManager.primaryColor.withOpacity(0.5),
|
||||
statusBarIconBrightness: Brightness.light,
|
||||
),
|
||||
child: SafeArea(
|
||||
child: Scaffold(
|
||||
backgroundColor: ColorsManager.backgroundColor,
|
||||
extendBodyBehindAppBar: true,
|
||||
extendBody: true,
|
||||
appBar: const DefaultAppBar(),
|
||||
body: Container(
|
||||
width: MediaQuery.sizeOf(context).width,
|
||||
height: MediaQuery.sizeOf(context).height,
|
||||
decoration: const BoxDecoration(
|
||||
image: DecorationImage(
|
||||
image: AssetImage(
|
||||
Assets.imagesBackground,
|
||||
),
|
||||
fit: BoxFit.cover,
|
||||
opacity: 0.4,
|
||||
),
|
||||
),
|
||||
child: selectedLight != null
|
||||
? LightInterface(light: selectedLight)
|
||||
: LightsViewList(lights: lights),
|
||||
),
|
||||
bottomNavigationBar: const DefaultNavBar(),
|
||||
),
|
||||
),
|
||||
bottomNavigationBar: const DefaultNavBar(),
|
||||
),
|
||||
),
|
||||
);
|
||||
},
|
||||
);
|
||||
},
|
||||
),
|
||||
|
||||
@@ -0,0 +1,37 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:syncrow_app/features/devices/view/widgets/lights/lights_list.dart';
|
||||
|
||||
import '../../../../shared_widgets/text_widgets/body_small.dart';
|
||||
import '../../../bloc/devices_cubit.dart';
|
||||
import '../../../model/light_model.dart';
|
||||
import '../universal_switch.dart';
|
||||
|
||||
class LightsViewList extends StatelessWidget {
|
||||
const LightsViewList({
|
||||
super.key,
|
||||
required this.lights,
|
||||
});
|
||||
|
||||
final List<LightModel> lights;
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Padding(
|
||||
padding: const EdgeInsets.only(top: 70, right: 15, left: 15, bottom: 80),
|
||||
child: SizedBox.expand(
|
||||
child: SingleChildScrollView(
|
||||
child: Column(
|
||||
crossAxisAlignment: CrossAxisAlignment.stretch,
|
||||
children: [
|
||||
const BodySmall(text: "All Lights"),
|
||||
UniversalSwitch(
|
||||
category: DevicesCubit.categories[1],
|
||||
),
|
||||
LightsList(lights: lights),
|
||||
],
|
||||
),
|
||||
),
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
@@ -13,7 +13,7 @@ class SceneCubit extends Cubit<SceneState> {
|
||||
void getScenes() {
|
||||
emit(SceneLoading());
|
||||
//TODO: remove this it's causing the Bad State because its being after the cubit is closed
|
||||
Future.delayed(const Duration(seconds: 5), () {
|
||||
Future.delayed(const Duration(milliseconds: 50), () {
|
||||
emit(SceneSuccess());
|
||||
});
|
||||
}
|
||||
|
||||
@@ -7,12 +7,17 @@ class DefaultContainer extends StatelessWidget {
|
||||
this.height,
|
||||
this.width,
|
||||
this.color,
|
||||
this.boxConstraints,
|
||||
this.margin,
|
||||
this.padding,
|
||||
});
|
||||
|
||||
final double? height;
|
||||
final double? width;
|
||||
final Widget child;
|
||||
|
||||
final BoxConstraints? boxConstraints;
|
||||
final EdgeInsets? margin;
|
||||
final EdgeInsets? padding;
|
||||
final Color? color;
|
||||
|
||||
@override
|
||||
@@ -20,11 +25,13 @@ class DefaultContainer extends StatelessWidget {
|
||||
return Container(
|
||||
height: height,
|
||||
width: width,
|
||||
margin: margin,
|
||||
constraints: boxConstraints,
|
||||
decoration: BoxDecoration(
|
||||
color: color ?? Colors.white,
|
||||
borderRadius: BorderRadius.circular(20),
|
||||
),
|
||||
padding: const EdgeInsets.all(10),
|
||||
padding: padding ?? const EdgeInsets.all(10),
|
||||
child: child,
|
||||
);
|
||||
}
|
||||
|
||||
@@ -8,6 +8,7 @@ class Assets {
|
||||
static const String iconsAutomatedClock = 'assets/icons/automated_clock.svg';
|
||||
static const String iconsCO2 = 'assets/icons/CO2.svg';
|
||||
static const String iconsColdMode = 'assets/icons/coldMode.svg';
|
||||
static const String iconsColorWheel = 'assets/icons/color_wheel.svg';
|
||||
static const String iconsCurtain = 'assets/icons/Curtain.svg';
|
||||
static const String iconsDashboard = 'assets/icons/dashboard.svg';
|
||||
static const String iconsDashboardFill = 'assets/icons/dashboard-fill.svg';
|
||||
@@ -22,6 +23,7 @@ class Assets {
|
||||
static const String iconsGateway = 'assets/icons/Gateway.svg';
|
||||
static const String iconsHome = 'assets/icons/home.svg';
|
||||
static const String iconsHot1 = 'assets/icons/hot1.jpg';
|
||||
static const String iconsKalvin = 'assets/icons/kalvin.svg';
|
||||
static const String iconsLayout = 'assets/icons/Layout.svg';
|
||||
static const String iconsLayoutFill = 'assets/icons/Layout-fill.svg';
|
||||
static const String iconsLight = 'assets/icons/Light.svg';
|
||||
|
||||
@@ -1,7 +1,6 @@
|
||||
// ignore_for_file: avoid_print
|
||||
|
||||
import 'package:flutter_bloc/flutter_bloc.dart';
|
||||
import 'package:syncrow_app/features/devices/bloc/devices_cubit.dart';
|
||||
|
||||
class MyBlocObserver extends BlocObserver {
|
||||
@override
|
||||
@@ -25,9 +24,6 @@ class MyBlocObserver extends BlocObserver {
|
||||
@override
|
||||
void onClose(BlocBase bloc) {
|
||||
super.onClose(bloc);
|
||||
if (bloc is DevicesCubit) {
|
||||
DevicesCubit.clearCategoriesSelection();
|
||||
}
|
||||
print('onClose -- ${bloc.runtimeType}');
|
||||
}
|
||||
}
|
||||
|
||||
@@ -3,6 +3,7 @@ import 'package:flutter/material.dart';
|
||||
abstract class ColorsManager {
|
||||
static const Color textPrimaryColor = Color(0xFF5D5D5D);
|
||||
static const Color primaryColor = Color(0xFF0030CB);
|
||||
static Color primaryWithOpacity = const Color(0xFF023DFE).withOpacity(0.6);
|
||||
static const Color onPrimaryColor = Colors.white;
|
||||
static const Color secondaryColor = Color(0xFF023DFE);
|
||||
static const Color onSecondaryColor = Color(0xFF023DFE);
|
||||
@@ -10,4 +11,8 @@ abstract class ColorsManager {
|
||||
|
||||
static const Color greyColor = Color(0xFFd5d5d5);
|
||||
static const Color backgroundColor = Color(0xFFececec);
|
||||
static const Color dozeColor = Color(0xFFFEC258);
|
||||
static const Color relaxColor = Color(0xFFFBD288);
|
||||
static const Color readingColor = Color(0xFFF7D69C);
|
||||
static const Color energizingColor = Color(0xFFEDEDED);
|
||||
}
|
||||
|
||||
@@ -24,4 +24,12 @@ class StringsManager {
|
||||
static const summerMode = 'Summer Mode';
|
||||
static const on = 'ON';
|
||||
static const off = 'OFF';
|
||||
static const timer = 'Timer';
|
||||
static const dimmerAndColor = "Dimmer & color";
|
||||
static const recentlyUsed = "Recently used colors";
|
||||
static const lightingModes = "Lighting modes";
|
||||
static const doze = "Doze";
|
||||
static const relax = "Relax";
|
||||
static const reading = "Reading";
|
||||
static const energizing = "Energizing";
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user