├── README.md ├── hover.py ├── main.py └── main.kv /README.md: -------------------------------------------------------------------------------- 1 | # Admin-Dashboard challage 2 | 3 | ### Written with python3.86, kivy==2.0.0rc4 and kivymd==master 4 | -------------------------------------------------------------------------------- /hover.py: -------------------------------------------------------------------------------- 1 | from kivy.base import runTouchApp 2 | from kivy.factory import Factory 3 | from kivymd.uix.list import OneLineAvatarListItem, IconLeftWidget 4 | from kivy.properties import BooleanProperty, ObjectProperty 5 | from kivy.core.window import Window 6 | from kivymd.uix.button import MDFlatButton, MDRaisedButton 7 | from kivy.utils import get_color_from_hex 8 | 9 | 10 | class HoverBehavior(object): 11 | hovered = BooleanProperty(False) 12 | border_point = ObjectProperty(None) 13 | 14 | def __init__(self, **kwargs): 15 | self.register_event_type('on_enter') 16 | self.register_event_type('on_leave') 17 | Window.bind(mouse_pos=self.on_mouse_pos) 18 | super(HoverBehavior, self).__init__(**kwargs) 19 | 20 | def on_mouse_pos(self, *args): 21 | if not self.get_root_window(): 22 | return 23 | pos = args[1] 24 | inside = self.collide_point(*self.to_widget(*pos)) 25 | if self.hovered == inside: 26 | return 27 | self.border_point = pos 28 | self.hovered = inside 29 | if inside: 30 | self.dispatch('on_enter') 31 | else: 32 | self.dispatch('on_leave') 33 | 34 | def on_enter(self): 35 | pass 36 | 37 | def on_leave(self): 38 | pass 39 | 40 | 41 | Factory.register('HoverBehavior', HoverBehavior) 42 | 43 | 44 | class HoverFlatBtn(MDFlatButton, HoverBehavior): 45 | def on_enter(self, *args): 46 | self.md_bg_color = (1, 1, 1, 1) 47 | 48 | def on_leave(self, *args): 49 | self.md_bg_color = get_color_from_hex('#e62e00') 50 | 51 | 52 | class HoverIconList(OneLineAvatarListItem, HoverBehavior): 53 | def on_enter(self, *args): 54 | self.bg_color = [1, 1, 1, 1] 55 | self.theme_text_color = "Custom" 56 | self.text_color = [0, 0, 1, 1] 57 | 58 | def on_leave(self, *args): 59 | self.bg_color = 0, 0, 1, 1 60 | self.theme_text_color = "Custom" 61 | self.text_color = 1, 1, 1, 1 62 | -------------------------------------------------------------------------------- /main.py: -------------------------------------------------------------------------------- 1 | from kivymd.app import MDApp 2 | from kivymd.uix.boxlayout import MDBoxLayout 3 | from kivymd_extensions.akivymd.uix.piechart import AKPieChart 4 | from kivymd.uix.datatables import MDDataTable 5 | from hover import HoverIconList 6 | from kivy.metrics import dp 7 | 8 | 9 | class Dashboard(MDBoxLayout): 10 | def __init__(self, **kwargs): 11 | super(Dashboard, self).__init__(**kwargs) 12 | 13 | self.update_tables() 14 | self.draw_chart() 15 | 16 | def update_tables(self): 17 | dt = MDDataTable(size_hint=(1, 1), 18 | elevation=-1, 19 | column_data=[ 20 | ("Product", dp(30)), 21 | ("Order ID", dp(30)), 22 | ("Purchased On", dp(30)), 23 | ("Amount", dp(30)), 24 | ("Tracking", dp(30)), 25 | ("Status", dp(30)), 26 | ], 27 | row_data=[ 28 | ( 29 | "MacBook Pro", 30 | "#325689526", 31 | "8th Dec 2020", 32 | "& 1255.99", 33 | "GDKJSBC45", 34 | ("alert", [255 / 256, 165 / 256, 0, 1], "Pending") 35 | ), 36 | ( 37 | "iPhone 11 Pro", 38 | "#325689526", 39 | "8th Dec 2020", 40 | "& 105.99", 41 | "GDKJSBC45", 42 | ("checkbox-marked-circle", [0, 1, 0, 1], "Delivered") 43 | ), 44 | ( 45 | "MacBook Air", 46 | "#325689526", 47 | "8th Dec 2020", 48 | "& 120.00", 49 | "GDKJSBC45", 50 | ("checkbox-marked-circle", [0, 1, 0, 1], "Delivered") 51 | ), 52 | ( 53 | "Oppo A20", 54 | "#325689526", 55 | "8th Dec 2020", 56 | "& 75.00", 57 | "GDKJSBC45", 58 | ("checkbox-marked-circle", [0, 1, 0, 1], "Delivered") 59 | ), 60 | ( 61 | "Samsung A50", 62 | "#325689526", 63 | "8th Dec 2020", 64 | "& 88.00", 65 | "GDKJSBC45", 66 | ("alert-circle", [1, 0, 0, 1], "Canceled") 67 | ), 68 | ( 69 | "MacBook Pro", 70 | "#327689146", 71 | "8th Dec 2020", 72 | "& 1205.99", 73 | "GDKJSBC45", 74 | ("checkbox-marked-circle", [0, 1, 0, 1], "Delivered") 75 | ) 76 | ]) 77 | self.ids.display.add_widget(dt) 78 | 79 | def draw_chart(self): 80 | self.items = [{ 81 | "Electronics": 40, 82 | "Laptops": 20, 83 | "Shoes": 20, 84 | "iPhones": 20 85 | }] 86 | self.piechart = AKPieChart( 87 | items=self.items, pos_hint={'center_x': 0.5, 'center_y': .4}, 88 | size_hint=[None, None], 89 | size=(dp(200), dp(200)) 90 | ) 91 | self.ids.pchart.add_widget(self.piechart) 92 | 93 | 94 | class MainApp(MDApp): 95 | def build(self): 96 | return Dashboard() 97 | 98 | 99 | if __name__ == "__main__": 100 | MainApp().run() 101 | -------------------------------------------------------------------------------- /main.kv: -------------------------------------------------------------------------------- 1 | : 2 | md_bg_color: .95,.95,.95,.95 3 | elevation: 1 4 | LeftBar: 5 | orientation: "vertical" 6 | size_hint_x: .15 7 | Label: 8 | size_hint_y: .1 9 | text: 'Cash Market' 10 | font_size: 20 11 | bold: True 12 | Label: 13 | size_hint_y: .1 14 | BoxLayout: 15 | size_hint_y: .4 16 | orientation: "vertical" 17 | HoverIconList: 18 | bold: True 19 | text: "Dashboard" 20 | LeftIcon: 21 | icon: "apps" 22 | HoverIconList: 23 | text: "Orders" 24 | LeftIcon: 25 | icon: "basket-plus-outline" 26 | HoverIconList: 27 | text: "Products" 28 | LeftIcon: 29 | icon: "gift-outline" 30 | HoverIconList: 31 | text: "Reports" 32 | LeftIcon: 33 | icon: "finance" 34 | HoverIconList: 35 | text: "Messages" 36 | LeftIcon: 37 | icon: "email" 38 | HoverIconList: 39 | text: "Customers" 40 | LeftIcon: 41 | icon: "account-supervisor" 42 | Label: 43 | size_hint_y: .2 44 | Label: 45 | size_hint_y: .1 46 | markup: True 47 | text: '[size=20][b] Cash Market[/b][/size]\n [size=15]All Rights Reserved[/size]' 48 | Widget: 49 | size_hint_y: .1 50 | BoxLayout: 51 | orientation: 'vertical' 52 | size_hint_x: .85 53 | MDBoxLayout: 54 | padding: 20, 20, 20, 0 55 | size_hint_y: .08 56 | md_bg_color: 1,1,1,1 57 | Widget: 58 | size_hint_x: .8 59 | Profile: 60 | size_hint_x: .07 61 | MDLabel: 62 | markup: True 63 | size_hint_x: .13 64 | text: '[b]Lazarus Muya[/b]\n Admin' 65 | MDSeparator: 66 | BoxLayout: 67 | size_hint_y: .22 68 | GridLayout: 69 | cols: 3 70 | spacing: 10 71 | padding: 5 72 | MDCard: 73 | size_hint: 1, 1 74 | radius: 10, 10 75 | elevation: -1 76 | padding: 15 77 | BoxLayout: 78 | size_hint_x: .7 79 | orientation: 'vertical' 80 | Label: 81 | MDLabel: 82 | text: "Total Sales" 83 | MDLabel: 84 | text: "$450.000" 85 | bold: True 86 | color: 0,0,1,1 87 | MDLabel: 88 | markup: True 89 | text: "[b]+45%[/b] this week" 90 | Label: 91 | BoxLayout: 92 | size_hint_x: .3 93 | MDIconButton: 94 | icon: "finance" 95 | user_font_size: '50sp' 96 | theme_text_color: "Custom" 97 | text_color: 0,0,1,1 98 | pos_hint: {'y': .2} 99 | MDCard: 100 | size_hint: 1, 1 101 | radius: 10, 10 102 | elevation: -1 103 | padding: 15 104 | BoxLayout: 105 | size_hint_x: .7 106 | orientation: 'vertical' 107 | Label: 108 | MDLabel: 109 | text: "Total Revenue" 110 | MDLabel: 111 | text: "$920.000" 112 | bold: True 113 | color: 0,0,1,1 114 | MDLabel: 115 | markup: True 116 | text: "[b]+60%[/b] this week" 117 | Label: 118 | BoxLayout: 119 | size_hint_x: .3 120 | MDIconButton: 121 | icon: "currency-usd-circle-outline" 122 | user_font_size: '50sp' 123 | theme_text_color: "Custom" 124 | text_color: 0,0,1,1 125 | pos_hint: {'y': .2} 126 | MDCard: 127 | size_hint: 1, 1 128 | radius: 10, 10 129 | elevation: -1 130 | padding: 15 131 | BoxLayout: 132 | size_hint_x: .7 133 | orientation: 'vertical' 134 | Label: 135 | MDLabel: 136 | text: "Today's Visitors" 137 | MDLabel: 138 | text: "2,560" 139 | bold: True 140 | color: 0,0,1,1 141 | MDLabel: 142 | markup: True 143 | text: "[b]+20%[/b] this week" 144 | Label: 145 | BoxLayout: 146 | size_hint_x: .3 147 | MDIconButton: 148 | icon: "account-supervisor" 149 | user_font_size: '50sp' 150 | theme_text_color: "Custom" 151 | text_color: 0,0,1,1 152 | pos_hint: {'y': .2} 153 | 154 | BoxLayout: 155 | size_hint_y: .7 156 | padding_x: 10 157 | BoxLayout: 158 | size_hint_x: .8 159 | orientation: 'vertical' 160 | padding: 10, 0, 0, 0 161 | BoxLayout: 162 | size_hint_y: .1 163 | padding: 0,0,0,10 164 | spacing: 20 165 | MDLabel: 166 | text: "Recent Orders" 167 | bold: True 168 | size_hint_x: .4 169 | MDTextFieldRound: 170 | hint_text: "search" 171 | size_hint_x: .3 172 | icon_left: "magnify" 173 | normal_color: 1,1,1,1 174 | color_active: 1,1,1,1 175 | MDDropDownItem: 176 | size_hint_x: .3 177 | text: "This week" 178 | 179 | BoxLayout: 180 | size_hint_y: .9 181 | id: display 182 | BoxLayout: 183 | size_hint_x: .2 184 | orientation: 'vertical' 185 | padding: 10 186 | spacing: 10 187 | MDLabel: 188 | size_hint_y: .06 189 | text: "Sales by Category" 190 | bold: True 191 | MDCard: 192 | id: pchart 193 | size_hint: 1, .45 194 | orientation: 'vertical' 195 | radius: 10, 10 196 | elevation: -1 197 | MDCard: 198 | size_hint: 1, .45 199 | orientation: 'vertical' 200 | radius: 10, 10 201 | elevation: -1 202 | padding: 20 203 | MDLabel: 204 | text: "Delivery Progress" 205 | bold: True 206 | Widget: 207 | MDLabel: 208 | text: "iPhone X 60%" 209 | MDProgressBar: 210 | value: 60 211 | color: 0,0,1,1 212 | MDLabel: 213 | text: "iPhone X 40%" 214 | MDProgressBar: 215 | value: 40 216 | color: 0,0,1,1 217 | MDLabel: 218 | text: "iPhone X 20%" 219 | MDProgressBar: 220 | value: 20 221 | color: 0,0,1,1 222 | Widget: 223 | 224 | 225 | : 226 | canvas.before: 227 | Color: 228 | rgba: 0,0,1,1 229 | Rectangle: 230 | pos: self.pos 231 | size: self.size 232 | 233 | : 234 | theme_text_color: "Custom" 235 | text_color: 0,.8,0,1 236 | 237 | : 238 | canvas.before: 239 | Ellipse: 240 | source: "mwas.jpg" 241 | size: 50, 50 242 | pos: self.pos --------------------------------------------------------------------------------