Add All the files from the touchpad_demonstrator Flutter App which can be build for Android and iOS
This commit is contained in:
Executable
+146
@@ -0,0 +1,146 @@
|
||||
import 'dart:async';
|
||||
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:touch_demonstrator/src/blocs/BlocProvider.dart';
|
||||
|
||||
import 'package:touch_demonstrator/model/touchData.dart';
|
||||
import 'package:touch_demonstrator/src/blocs/bluetoothBloc.dart';
|
||||
|
||||
class DebugView extends StatefulWidget {
|
||||
/// Screen that shows RAW data from the bluetooth device
|
||||
@override
|
||||
_DebugViewState createState() => _DebugViewState();
|
||||
}
|
||||
|
||||
class _DebugViewState extends State<DebugView> {
|
||||
ScrollController _scrollController;
|
||||
static const TextStyle textStyleWhite = TextStyle(color: Colors.white);
|
||||
static const TextStyle textStyleBlack = TextStyle(color: Colors.black);
|
||||
|
||||
@override
|
||||
void initState() {
|
||||
super.initState();
|
||||
_scrollController = ScrollController();
|
||||
}
|
||||
|
||||
void _scrollList() {
|
||||
Future.delayed(Duration(milliseconds: 50), () {
|
||||
_scrollController.animateTo(_scrollController.position.maxScrollExtent,
|
||||
duration: new Duration(milliseconds: 500), curve: Curves.easeOut);
|
||||
});
|
||||
}
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
final BluetoothBloc bloc = BlocProvider.of(context).bluetoothBlocGetter;
|
||||
return Scaffold(
|
||||
appBar: AppBar(
|
||||
title: Text('Debug View Page'),
|
||||
),
|
||||
body: SafeArea(
|
||||
child: Column(
|
||||
children: <Widget>[
|
||||
_buildHeaderDebugPage(context),
|
||||
// Divider(),
|
||||
StreamBuilder<List<TouchData>>(
|
||||
key: Key('ListTouchData'),
|
||||
stream: bloc.getHistory$,
|
||||
builder: (BuildContext context,
|
||||
AsyncSnapshot<List<TouchData>> snapshot) {
|
||||
if (snapshot.hasData) {
|
||||
_scrollList();
|
||||
print('${snapshot.data.length}');
|
||||
Color colorOfContainer;
|
||||
return Expanded(
|
||||
child: SizedBox(
|
||||
height: 50.0,
|
||||
child: ListView.builder(
|
||||
reverse: false,
|
||||
controller: _scrollController,
|
||||
scrollDirection: Axis.vertical,
|
||||
itemCount: snapshot.data.length,
|
||||
itemExtent: 33.0,
|
||||
itemBuilder: (context, i) {
|
||||
return buildRowOfTouchData(
|
||||
colorOfContainer, i, snapshot);
|
||||
}),
|
||||
));
|
||||
} else {
|
||||
return Container();
|
||||
}
|
||||
}),
|
||||
],
|
||||
),
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
Container _buildHeaderDebugPage(BuildContext context) {
|
||||
return Container(
|
||||
color: Theme.of(context).accentColor,
|
||||
child: Padding(
|
||||
padding: const EdgeInsets.all(8.0),
|
||||
child: Row(
|
||||
children: <Widget>[
|
||||
debugListItem('#', flexItem: 1),
|
||||
debugListItem('Finger'),
|
||||
debugListItem('Event'),
|
||||
debugListItem('X'),
|
||||
debugListItem('Y'),
|
||||
],
|
||||
),
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
Container buildRowOfTouchData(Color colorOfContainer, int _index,
|
||||
AsyncSnapshot<List<TouchData>> snapshot) {
|
||||
var _textStyleDebug;
|
||||
var _fingerNrText = '${snapshot.data[_index].fingerNumber}';
|
||||
var _eventText;
|
||||
var _xText = '${snapshot.data[_index].x.toString().padLeft(4, ' ')}';
|
||||
var _yText = '${snapshot.data[_index].y.toString().padLeft(4, ' ')}';
|
||||
|
||||
if ((snapshot.data[_index].event) == 1) {
|
||||
_eventText = 'MOVE';
|
||||
_textStyleDebug = textStyleBlack;
|
||||
colorOfContainer = Colors.white;
|
||||
} else {
|
||||
_textStyleDebug = textStyleWhite;
|
||||
if ((snapshot.data[_index].event) == 4) {
|
||||
colorOfContainer = Colors.teal;
|
||||
_eventText = 'DOWN';
|
||||
} else if((snapshot.data[_index].event) == 5){
|
||||
_eventText = 'UP';
|
||||
colorOfContainer = Colors.purple;
|
||||
} else {
|
||||
print('Default ${snapshot.data[_index]}');
|
||||
return Container();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
return Container(
|
||||
color: colorOfContainer,
|
||||
child: Row(
|
||||
children: <Widget>[
|
||||
debugListItem('$_index', flexItem: 1, styleText: _textStyleDebug),
|
||||
debugListItem(_fingerNrText, styleText: _textStyleDebug),
|
||||
debugListItem(_eventText, styleText: _textStyleDebug),
|
||||
debugListItem(_xText, styleText: _textStyleDebug),
|
||||
debugListItem(_yText, styleText: _textStyleDebug),
|
||||
],
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
Expanded debugListItem(String textItem,
|
||||
{int flexItem = 2, TextStyle styleText = textStyleWhite}) {
|
||||
return Expanded(
|
||||
flex: flexItem,
|
||||
child: Center(
|
||||
child: Text(textItem, style: styleText),
|
||||
),
|
||||
);
|
||||
}
|
||||
}
|
||||
Executable
+180
@@ -0,0 +1,180 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:touch_demonstrator/ui/pageTouchPoints/AppBarPageTouchPoints.dart';
|
||||
import 'package:touch_demonstrator/ui/pageTouchPoints/SideBar.dart';
|
||||
import 'dart:core';
|
||||
import 'package:touch_demonstrator/src/blocs/BlocProvider.dart'; //bloc:
|
||||
import 'package:touch_demonstrator/ui/pageTouchPoints/ScanResultBottomSheet.dart';
|
||||
import 'package:touch_demonstrator/ui/pageTouchPoints/ButtonOrAnimation.dart';
|
||||
import 'package:touch_demonstrator/ui/pageTouchPoints/Logo.dart';
|
||||
import 'package:touch_demonstrator/ui/pageTouchPoints/Sensor.dart';
|
||||
import 'package:flutter_blue/flutter_blue.dart';
|
||||
import 'package:vibrate/vibrate.dart';
|
||||
import 'package:touch_demonstrator/model/vibrate.dart';
|
||||
|
||||
class PageTouchPoints extends StatefulWidget {
|
||||
PageTouchPoints({Key key, this.title}) : super(key: key);
|
||||
final String title;
|
||||
|
||||
@override
|
||||
_PageTouchPointsState createState() => new _PageTouchPointsState();
|
||||
}
|
||||
|
||||
class _PageTouchPointsState extends State<PageTouchPoints> {
|
||||
final GlobalKey<ScaffoldState> mScaffoldState =
|
||||
new GlobalKey<ScaffoldState>();
|
||||
static Modal modal;
|
||||
static bool firstTime = true;
|
||||
|
||||
@override
|
||||
void dispose() {
|
||||
final bBloc = BlocProvider.of(context).bluetoothBlocGetter;
|
||||
bBloc.disconnect.add(null); //disconnect everything
|
||||
super.dispose();
|
||||
}
|
||||
|
||||
@override
|
||||
void didChangeDependencies() {
|
||||
super.didChangeDependencies();
|
||||
print('didChangeDependencies');
|
||||
|
||||
/// Manages Snackbar "no device found" and "Bluetooth off" and toggles the debugmode.
|
||||
final bBloc = BlocProvider.of(context).bluetoothBlocGetter;
|
||||
final debugBloc = BlocProvider.of(context).debugBlocGetter;
|
||||
|
||||
_showSnackbar(String textInSnackBar) {
|
||||
/// Shows Snackbar for 0.5 s with String textInSnackBar in it
|
||||
print('snackbar $textInSnackBar');
|
||||
mScaffoldState.currentState.showSnackBar(SnackBar(
|
||||
content: Text(
|
||||
textInSnackBar,
|
||||
style: TextStyle(fontSize: 15),
|
||||
),
|
||||
duration: Duration(milliseconds: 1000),
|
||||
));
|
||||
}
|
||||
|
||||
_toggleDebug(bool debugStatus) {
|
||||
vibrate(FeedbackType.success);
|
||||
_showSnackbar('Debug View: ${debugStatus ? 'enabled' : 'disabled'}!');
|
||||
}
|
||||
|
||||
if (firstTime) {
|
||||
firstTime = false;
|
||||
modal = new Modal();
|
||||
bBloc.devicesFound$.listen((device) {
|
||||
if (device.length == 0) {
|
||||
print('Snackbar: No device found');
|
||||
_showSnackbar('No device found');
|
||||
vibrateDelayed(FeedbackType.warning, Duration(milliseconds: 150));
|
||||
} else {
|
||||
modal.connectBottomSheet(context, device);
|
||||
}
|
||||
});
|
||||
debugBloc.debugEnabledStatus$.listen((data) => _toggleDebug(data));
|
||||
|
||||
bBloc.bluetoothState$
|
||||
.where((bluetoothState) => bluetoothState == BluetoothState.off)
|
||||
.listen(
|
||||
(bluetoothState) => _showBluetoothOffSnackbar(bluetoothState));
|
||||
|
||||
bBloc.bluetoothState$
|
||||
.where((bluetoothState) => bluetoothState == BluetoothState.on)
|
||||
.listen((_) => mScaffoldState.currentState.removeCurrentSnackBar());
|
||||
} else {
|
||||
print('REMOVE current snack bar');
|
||||
mScaffoldState.currentState.removeCurrentSnackBar();
|
||||
}
|
||||
}
|
||||
|
||||
_showBluetoothOffSnackbar(BluetoothState bluetoothState) {
|
||||
/// Shows Snackbar if Bluetooth is off to inform user.
|
||||
var textInSnackbar = 'Bluetooth is off!';
|
||||
|
||||
print('snackbar $textInSnackbar');
|
||||
mScaffoldState.currentState.showSnackBar(SnackBar(
|
||||
backgroundColor: Colors.red,
|
||||
content: Row(
|
||||
mainAxisAlignment: MainAxisAlignment.start,
|
||||
children: <Widget>[
|
||||
Icon(Icons.warning),
|
||||
Padding(
|
||||
padding: EdgeInsets.only(left: 10.0),
|
||||
child: Text(
|
||||
textInSnackbar,
|
||||
textAlign: TextAlign.center,
|
||||
style: TextStyle(fontSize: 25),
|
||||
),
|
||||
),
|
||||
],
|
||||
),
|
||||
duration: Duration(days: 1),
|
||||
));
|
||||
}
|
||||
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
/// build UI for the main screen in the app
|
||||
return Scaffold(
|
||||
key: mScaffoldState,
|
||||
// necessary for toast message
|
||||
appBar: buildAppBarPageTouchPoints(context),
|
||||
drawer: LeftDrawer(),
|
||||
body: SafeArea(child: OrientationBuilder(builder: (context, orientation) {
|
||||
return _buildBody(orientation);
|
||||
// return _buildVerticalLayout();
|
||||
})),
|
||||
);
|
||||
}
|
||||
|
||||
_buildBody(Orientation orientation) {
|
||||
if (orientation == Orientation.portrait)
|
||||
return _buildVerticalLayout();
|
||||
else
|
||||
return _buildHorizontalLayout();
|
||||
}
|
||||
|
||||
static const _heightLogo = 100.0;
|
||||
|
||||
_buildVerticalLayout() {
|
||||
/// Layout for vertical orientation
|
||||
EdgeInsets devicePadding = MediaQuery.of(context).padding;
|
||||
return Padding(
|
||||
padding: const EdgeInsets.all(5.0),
|
||||
child: Column(
|
||||
mainAxisAlignment: MainAxisAlignment.start,
|
||||
children: <Widget>[
|
||||
Container(height: devicePadding.top),
|
||||
LogoWithText(_heightLogo),
|
||||
Expanded(child: Sensor()),
|
||||
ConnectButtonWithAnimations(),
|
||||
],
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
_buildHorizontalLayout() {
|
||||
/// Layout for horizontal orientation
|
||||
return Padding(
|
||||
padding: const EdgeInsets.all(8.0),
|
||||
child: Column(children: <Widget>[
|
||||
Row(
|
||||
mainAxisAlignment: MainAxisAlignment.center,
|
||||
children: <Widget>[
|
||||
Column(
|
||||
mainAxisAlignment: MainAxisAlignment.start,
|
||||
children: <Widget>[
|
||||
LogoWithText(_heightLogo),
|
||||
ConnectButtonWithAnimations(),
|
||||
],
|
||||
),
|
||||
Column(
|
||||
children: <Widget>[
|
||||
Sensor(),
|
||||
],
|
||||
),
|
||||
],
|
||||
),
|
||||
]),
|
||||
);
|
||||
}
|
||||
}
|
||||
Executable
+52
@@ -0,0 +1,52 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter/services.dart';
|
||||
import 'package:webview_flutter/webview_flutter.dart';
|
||||
import 'dart:async';
|
||||
|
||||
class SideBarContent extends StatefulWidget {
|
||||
final String html;
|
||||
final String title;
|
||||
|
||||
SideBarContent({this.title, this.html});
|
||||
|
||||
@override
|
||||
SideBarContentState createState() {
|
||||
return new SideBarContentState();
|
||||
}
|
||||
}
|
||||
|
||||
class SideBarContentState extends State<SideBarContent> {
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
return Scaffold(
|
||||
appBar: AppBar(
|
||||
title: Text('${widget.title}'),
|
||||
),
|
||||
body: SafeArea(
|
||||
child: FutureBuilder<String>(
|
||||
future: LocalLoader().loadLocal(widget.html),
|
||||
builder: (context, snapshot) {
|
||||
if (snapshot.hasData) {
|
||||
return WebView(
|
||||
// HTML code loaded from file
|
||||
initialUrl: new Uri.dataFromString(snapshot.data,
|
||||
mimeType: 'text/html')
|
||||
.toString(),
|
||||
javascriptMode: JavascriptMode.unrestricted,
|
||||
);
|
||||
} else if (snapshot.hasError) {
|
||||
return Text("Error trying to load HTML FIle: ${snapshot.error}");
|
||||
} else {
|
||||
return Container();
|
||||
}
|
||||
})));
|
||||
}
|
||||
}
|
||||
|
||||
class LocalLoader {
|
||||
Future<String> loadLocal(String html) async {
|
||||
String response = await rootBundle.loadString(html);
|
||||
// return await rootBundle.loadString('assets/yourFile.html');
|
||||
return response;
|
||||
}
|
||||
}
|
||||
Executable
+62
@@ -0,0 +1,62 @@
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:touch_demonstrator/ui/pageTouchPoints/uiComponents.dart';
|
||||
import 'package:touch_demonstrator/ui/pageTouchPoints/Logo.dart';
|
||||
EdgeInsets devicePadding;
|
||||
|
||||
class StartPage extends StatelessWidget {
|
||||
@override
|
||||
Widget build(BuildContext context) {
|
||||
devicePadding = MediaQuery.of(context).padding;
|
||||
return Scaffold(
|
||||
appBar: AppBar(
|
||||
leading: null,
|
||||
title: Text('Demo App'),
|
||||
),
|
||||
body: SafeArea(child: OrientationBuilder(builder: (context, orientation) {
|
||||
return orientation == Orientation.portrait
|
||||
? _buildVerticalLayout(context)
|
||||
: _buildHorizontalLayout(context);
|
||||
})),
|
||||
);
|
||||
}
|
||||
}
|
||||
const heightLogo = 100.0;
|
||||
|
||||
_buildVerticalLayout(BuildContext context) => Padding(
|
||||
padding: const EdgeInsets.only(left: 10.0, right: 10.0),
|
||||
child: Center(
|
||||
child: Column(
|
||||
mainAxisAlignment: MainAxisAlignment.start,
|
||||
children: <Widget>[
|
||||
Container(
|
||||
height: devicePadding.top,
|
||||
),
|
||||
TextAboveLogo(),
|
||||
Logo(heightLogo),
|
||||
TouchPad(),
|
||||
// Sensor(),
|
||||
Button(),
|
||||
],
|
||||
),
|
||||
),
|
||||
);
|
||||
|
||||
_buildHorizontalLayout(BuildContext context) => Padding(
|
||||
padding: const EdgeInsets.only(left: 10.0, right: 10.0),
|
||||
child: Row(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
|
||||
children: <Widget>[
|
||||
TouchPad(),
|
||||
// Sensor(),
|
||||
Center(
|
||||
child: Column(
|
||||
mainAxisAlignment: MainAxisAlignment.center,
|
||||
children: <Widget>[
|
||||
TextAboveLogo(),
|
||||
Logo(heightLogo),
|
||||
Button(),
|
||||
],
|
||||
),
|
||||
),
|
||||
],
|
||||
));
|
||||
Reference in New Issue
Block a user