import 'package:edge_alert/edge_alert.dart'; import 'package:flutter/foundation.dart'; import 'package:flutter/gestures.dart'; import 'package:flutter/material.dart'; import 'package:flutter/services.dart'; import 'package:flutter_material_color_picker/flutter_material_color_picker.dart'; import 'package:job_app/config/palette.dart'; import 'package:job_app/models/APiResponse.dart'; import 'package:job_app/models/CvModel.dart'; import 'package:job_app/models/fonts.dart'; import 'package:job_app/models/user/user.dart'; import 'package:job_app/services/Auth/getCurrentUser.dart'; import 'package:job_app/services/cv/addCvToUser.dart'; import 'package:job_app/services/cv/fonts.dart'; import 'package:job_app/singletons/cvModels.dart'; import 'package:job_app/singletons/user_info.dart'; import 'package:job_app/widgets/loading_screen.dart'; import 'package:ndialog/ndialog.dart'; import 'package:rflutter_alert/rflutter_alert.dart'; import 'package:webview_flutter/webview_flutter.dart'; class BuildCvModel extends StatefulWidget { const BuildCvModel({Key key}) : super(key: key); @override _BuildCvModelState createState() => _BuildCvModelState(); } class _BuildCvModelState extends State { bool isLoading = false; List fontsList = []; Color pickerColor = Color(0xffffffff); String colorString = "#ffffff"; int fontId; int modelId; String fontUrl; String modelValue; String fontValue; Map data; UserModel userModel = UserModel(); List cvModels = cvModelsSingleTons.cvModels; WebViewController _controller; String motivationLetter; TextEditingController motivationLetterController = TextEditingController(); GlobalKey _globalKey = GlobalKey(); Future getFonts() async { FontService request = FontService(); ApiResponseModel response = await request.getAllFonts(); setState(() { fontsList = response.data; }); } @override void initState() { // TODO: implement initState super.initState(); getFonts(); } Widget build(BuildContext context) { data = ModalRoute.of(context).settings.arguments; String test = data["language"]; String lanString = test.substring(1, test.length - 1); String secondSt = lanString.replaceAll(' ', ''); String lasSt = secondSt.replaceAll(',', '

'); String experienceString = data["experience"].substring(1, data["experience"].length - 1); List experienceList = experienceString.split(','); String languageString = data["language"].substring(1, data["language"].length - 1); List languageList = languageString.split(','); String trainingString = data["training"].substring(1, data["training"].length - 1); List trainingList = trainingString.split(','); String skillString = data["skill"].substring(1, data["skill"].length - 1); List skillList = skillString.split(','); return Stack(children: [ GestureDetector( onTap: () { FocusScope.of(context).requestFocus(new FocusNode()); }, child: Scaffold( body: SingleChildScrollView( child: Padding( padding: const EdgeInsets.fromLTRB(20, 30, 20, 0), child: Column( children: [ Row( mainAxisAlignment: MainAxisAlignment.spaceBetween, children: [ Text( "Build your CV", style: TextStyle( color: Colors.black, fontFamily: 'Montserrat', fontSize: 22), ), ], ), Text( "letters, as opposed to using 'Content here, content here', making it look like readable English. Many desktop publishing packages and web page editors now use Lorem Ipsum", style: TextStyle( color: Color.fromRGBO(0, 0, 0, 0.7), fontSize: 12, height: 2, fontFamily: 'MontserratExtraLight'), ), SizedBox( height: 0, ), Container( height: 500, width: double.maxFinite, child: WebView( initialUrl: "", onPageFinished: (String url) { _controller.evaluateJavascript( 'document.getElementById("IMAGE").src = "https://server.thejob.net${userInfo.user.image}"'); _controller.evaluateJavascript( 'document.getElementById("CITY").innerHTML = "${userInfo.user.city}"'); _controller.evaluateJavascript( 'document.getElementById("COUNTRY").innerHTML = "${userInfo.user.country}"'); _controller.evaluateJavascript( 'document.getElementById("EMAIL").innerHTML = "${userInfo.user.email}"'); _controller.evaluateJavascript( 'document.getElementById("PHONENUMBER").innerHTML = "${data["phonenumber"]}"'); _controller.evaluateJavascript( 'document.getElementById("JOBTITLE").innerHTML = "${data["jobtitle"]}"'); _controller.evaluateJavascript( 'document.getElementById("EXPERIENCES").innerHTML = "${data["experience"]}"'); _controller.evaluateJavascript( 'document.getElementById("SKILL").innerHTML = "${data["skill"]}"'); _controller.evaluateJavascript( 'document.getElementById("LANGUAGE").innerHTML = "$lasSt"'); _controller.evaluateJavascript( 'document.getElementById("FIRSTNAME").innerHTML = "${data["firstName"]}"'); _controller.evaluateJavascript( 'document.getElementById("LASTNAME").innerHTML = "${data["lastName"]}"'); _controller.evaluateJavascript( 'document.getElementById("INTRO").innerHTML = "${data["intro"]}"'); if (colorString.isNotEmpty) { _controller.evaluateJavascript( 'document.getElementById("SIDEBAR").style.backgroundColor = "$colorString" ; '); } if (fontUrl.isNotEmpty) { _controller.evaluateJavascript( "var newFont = new FontFace('theFont','url($fontUrl)',{});" "newFont.load().then(function (LoadedFace){document.fonts.add(LoadedFace);document.body.style.fontFamily='theFont,serif'});"); } }, onWebViewCreated: (WebViewController webViewController) { _controller = webViewController; _controller.loadUrl( "https://server.thejob.net${cvModels.first.file.url}"); //loadLocalHTML(); }, // gestureRecognizers: Set() // ..add(Factory( // () => VerticalDragGestureRecognizer(), // )), javascriptMode: JavascriptMode.unrestricted, ), ), Padding( padding: const EdgeInsets.only(top: 15), child: Row( mainAxisAlignment: MainAxisAlignment.spaceEvenly, children: [ modelDropDown(), Container( height: 30, width: 100, decoration: BoxDecoration(boxShadow: [ BoxShadow( color: Colors.grey.withOpacity(0.2), spreadRadius: 6, blurRadius: 6, offset: Offset(0, 6), ) ]), child: ElevatedButton( onPressed: () async { await NDialog( dialogStyle: DialogStyle(titleDivider: true), title: Text("Choose a color for your CV"), content: MaterialColorPicker( onColorChange: (Color color) { setState(() { pickerColor = color; colorString = pickerColor.toString(); String opString = colorString.substring( colorString.length - 7, colorString.length - 1); colorString = "#" + opString; _controller.evaluateJavascript( 'document.getElementById("SIDEBAR").style.backgroundColor = "$colorString" ; '); }); }, selectedColor: Colors.red), ).show(context); }, style: ButtonStyle( backgroundColor: MaterialStateProperty.all( Colors.white)), child: Row( mainAxisAlignment: MainAxisAlignment.spaceBetween, children: [ Text( "color", style: TextStyle( fontSize: 14, fontFamily: 'Montserrat', color: Colors.black), ), Container( width: 16, height: 16, decoration: BoxDecoration( color: pickerColor, borderRadius: BorderRadius.circular(100)), ) ], )), ), fontDropDown() ], ), ), Padding( padding: const EdgeInsets.only(top: 25, bottom: 25), child: Row( mainAxisAlignment: MainAxisAlignment.start, children: [ Text( "Motivation Letter", textAlign: TextAlign.start, style: TextStyle( color: Colors.black, fontFamily: 'Montserrat', fontSize: 16), ), ], ), ), Form( key: _globalKey, child: buildBigTextFormField(), ), Padding( padding: const EdgeInsets.fromLTRB(0, 10, 0, 40), child: Container( width: double.infinity, height: 45, decoration: BoxDecoration( color: Palette.primary, borderRadius: BorderRadius.circular(8)), child: TextButton( onPressed: () async { if (_globalKey.currentState.validate()) { setState(() { isLoading=true; }); AddCvToUserService response = AddCvToUserService(); ApiResponseModel apiResponse= await response.addCvToUser( color: colorString.isNotEmpty?colorString:'#ffffff', cvModelId: modelId==null?cvModelsSingleTons.cvModels.first.id :modelId, experience: experienceList, fontId: fontId==null?fontsList.first.id :fontId, introduction: data["intro"], language: languageList, motivationLetter: motivationLetter, name: "${data["firstName"]+' '+ data["lastName"]} CV", skills: skillList, training: trainingList, ); if(apiResponse.statusCode==406){ Alert( context: context, type: AlertType.warning, style: AlertStyle( animationType: AnimationType.shrink, ), title: "Model not acquired", desc: "do you want to buy this model?", buttons: [ DialogButton( color: Colors.grey, child: Text( "Cancel", style: TextStyle( fontFamily: 'MontserratRegular', fontSize: 18, color: Colors.white, fontWeight: FontWeight.bold), ), onPressed: () { Navigator.pop(context); }), DialogButton( color: Palette.primary, child: Text( "Proceed", style: TextStyle( fontFamily: 'MontserratRegular', fontSize: 18, color: Colors.white, fontWeight: FontWeight.bold), ), onPressed: () async{ setState(() { isLoading=true; }); Navigator.pop(context); ApiResponseModel buyCvModel = await response.buyCvModel(apiResponse.data); setState(() { isLoading=false; }); if(buyCvModel.statusCode==200 || buyCvModel.statusCode==201){ Alert( context: context, type: AlertType.success, style: AlertStyle( animationType: AnimationType.shrink, ), title: "Model has be added", desc: "You can now use this model for your CV", buttons: [ DialogButton( color: Palette.primary, child: Text( "Ok", style: TextStyle( fontFamily: 'MontserratRegular', fontSize: 18, color: Colors.white, fontWeight: FontWeight.bold), ), onPressed: () { Navigator.pop(context); }), ] ).show(); }else{ Alert( context: context, type: AlertType.error, title: "Please try again later", buttons: [ DialogButton( color: Palette.primary, child: Text( "Ok", style: TextStyle( fontFamily: 'MontserratRegular', fontSize: 18, color: Colors.white, fontWeight: FontWeight.bold), ), onPressed: () { Navigator.pop(context); }), ] ).show(); } }, ), ], ).show(); } else if(apiResponse.statusCode==200 || apiResponse.statusCode==201){ setState(() { isLoading=false; }); int count = 0; Navigator.popUntil(context, (route) { return count++ == 3; }); //Navigator.pushAndRemoveUntil(context, newRoute, (route) => false) } setState(() { isLoading=false; }); } }, child: Text( "Continue", style: TextStyle( fontSize: 22, color: Colors.white, fontFamily: 'MontserratRegular'), )), ), ), ], ), ), ), ), ), if (isLoading) LoadingScreen(), ]); } Widget modelDropDown() { return Container( padding: EdgeInsets.all(5), height: 30, width: 100, decoration: BoxDecoration( color: Colors.white, borderRadius: BorderRadius.circular(5), boxShadow: [ BoxShadow( color: Colors.grey.withOpacity(0.5), spreadRadius: 1, blurRadius: 7, offset: Offset(0, 3), ) ], ), child: DropdownButtonHideUnderline( child: DropdownButton( value: modelValue, icon: const Icon(Icons.keyboard_arrow_down_rounded), iconSize: 20, elevation: 16, isExpanded: true, style: const TextStyle( color: Colors.black, fontSize: 14, fontWeight: FontWeight.bold, fontFamily: 'Montserrat'), onChanged: (String newValue) { setState(() { modelValue = newValue; CvModelModel endpointCvModel = cvModels .where((element) => element.name.contains(modelValue)) .first; String url = "https://server.thejob.net${endpointCvModel.file.url}"; modelId = endpointCvModel.id; _controller.loadUrl(url); }); }, items: cvModels.map>((CvModelModel value) { return DropdownMenuItem( value: value.name, child: Text(value.name), ); }).toList(), hint: Text( "Models", style: TextStyle( color: Colors.black, fontSize: 14, fontWeight: FontWeight.bold, fontFamily: 'Montserrat'), ), ), ), ); } Widget fontDropDown() { return Container( padding: EdgeInsets.all(5), height: 30, width: 100, decoration: BoxDecoration( color: Colors.white, borderRadius: BorderRadius.circular(5), boxShadow: [ BoxShadow( color: Colors.grey.withOpacity(0.5), spreadRadius: 1, blurRadius: 7, offset: Offset(0, 3), ) ], ), child: DropdownButtonHideUnderline( child: DropdownButton( value: fontValue, icon: const Icon(Icons.keyboard_arrow_down_rounded), iconSize: 20, elevation: 16, isExpanded: true, style: const TextStyle( color: Colors.black, fontSize: 14, fontWeight: FontWeight.bold, fontFamily: 'Montserrat'), onChanged: (String newValue) { setState(() { fontValue = newValue; FontsModel selectedFont = fontsList .where((element) => element.name.contains(newValue)) .first; String url = 'https://server.thejob.net${selectedFont.url}'; _controller.evaluateJavascript( "var newFont = new FontFace('theFont','url($url)',{});" "newFont.load().then(function (LoadedFace){document.fonts.add(LoadedFace);document.body.style.fontFamily='theFont,serif'});"); fontUrl = url; fontId = selectedFont.id; }); }, items: fontsList.map>((FontsModel value) { return DropdownMenuItem( value: value.name.substring(0, value.name.length - 4), child: Text(value.name.substring(0, value.name.length - 4)), ); }).toList(), hint: Text( "Aa Fonts", style: TextStyle( color: Colors.black, fontSize: 14, fontWeight: FontWeight.bold, fontFamily: 'Montserrat'), ), ), ), ); } Widget buildBigTextFormField() { return Container( margin: EdgeInsets.only(bottom: 15), child: TextFormField( onChanged: (val) { setState(() { motivationLetter = val; }); }, controller: motivationLetterController, validator: (val) { if (val.isEmpty) { return "Please fill in your motivation letter"; } return null; }, maxLines: 5, keyboardType: TextInputType.multiline, autocorrect: false, cursorColor: Palette.primary, style: TextStyle( color: Colors.black, fontWeight: FontWeight.bold, fontSize: 22, fontFamily: 'MontserratExtraLight'), decoration: InputDecoration( contentPadding: EdgeInsets.fromLTRB(10, 10, 0, 0), hintStyle: TextStyle( color: Color.fromRGBO(0, 0, 0, 0.3), fontFamily: 'MontserratExtraLight', ), errorBorder: OutlineInputBorder( borderRadius: BorderRadius.circular(0), borderSide: BorderSide( color: Colors.red, )), focusedErrorBorder: OutlineInputBorder( borderRadius: BorderRadius.circular(0), borderSide: BorderSide( color: Colors.red, )), focusedBorder: OutlineInputBorder( borderRadius: BorderRadius.circular(0), borderSide: BorderSide( color: Color.fromRGBO(112, 112, 112, 0.8), )), enabledBorder: OutlineInputBorder( borderRadius: BorderRadius.circular(0), borderSide: BorderSide(color: Color.fromRGBO(112, 112, 112, 0.8)), ), ), ), ); } }