Compare commits
	
		
			7 Commits
		
	
	
		
			develop
			...
			feature-hi
		
	
	| Author | SHA1 | Date | |
|---|---|---|---|
| 5d264f7651 | |||
| a6f7c09671 | |||
| eaf6d9f547 | |||
| 5b34afd6cb | |||
| 25d901d093 | |||
| 6237a2e9cf | |||
| c4f5be2205 | 
@@ -1,9 +1,9 @@
 | 
			
		||||
import 'dart:convert';
 | 
			
		||||
import 'dart:developer';
 | 
			
		||||
 | 
			
		||||
import 'package:localstore/localstore.dart';
 | 
			
		||||
 | 
			
		||||
import 'apiResponse.dart';
 | 
			
		||||
import 'webuntis/webuntisError.dart';
 | 
			
		||||
 | 
			
		||||
abstract class RequestCache<T extends ApiResponse?> {
 | 
			
		||||
  static const int cacheNothing = 0;
 | 
			
		||||
@@ -30,16 +30,18 @@ abstract class RequestCache<T extends ApiResponse?> {
 | 
			
		||||
      if(renew == null || !renew!) return;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    T? newValue;
 | 
			
		||||
    try {
 | 
			
		||||
      T newValue = await onLoad();
 | 
			
		||||
      onUpdate(newValue);
 | 
			
		||||
      newValue = await onLoad();
 | 
			
		||||
      onUpdate(newValue as T);
 | 
			
		||||
 | 
			
		||||
      Localstore.instance.collection(file).doc(document).set({
 | 
			
		||||
        'json': jsonEncode(newValue),
 | 
			
		||||
        'lastupdate': DateTime.now().millisecondsSinceEpoch
 | 
			
		||||
      });
 | 
			
		||||
    } on WebuntisError catch(e) {
 | 
			
		||||
      onError(e);
 | 
			
		||||
    } catch(e) {
 | 
			
		||||
      log("Error while fetching/ parsing. Raw server response: ${newValue?.rawResponse.body ?? "no response"}");
 | 
			
		||||
      onError(Exception(e.toString()));
 | 
			
		||||
    }
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
 
 | 
			
		||||
@@ -29,6 +29,7 @@ import 'storage/base/settingsProvider.dart';
 | 
			
		||||
import 'theming/darkAppTheme.dart';
 | 
			
		||||
import 'theming/lightAppTheme.dart';
 | 
			
		||||
import 'view/login/login.dart';
 | 
			
		||||
import 'view/pages/more/abiturCalculator/models/abiturCalculatorModel.dart';
 | 
			
		||||
import 'widget/placeholderView.dart';
 | 
			
		||||
 | 
			
		||||
Future<void> main() async {
 | 
			
		||||
@@ -68,6 +69,8 @@ Future<void> main() async {
 | 
			
		||||
 | 
			
		||||
          ChangeNotifierProvider(create: (context) => MessageProps()),
 | 
			
		||||
          ChangeNotifierProvider(create: (context) => HolidaysProps()),
 | 
			
		||||
 | 
			
		||||
          ChangeNotifierProvider(create: (context) => AbiturCalculatorModel()),
 | 
			
		||||
        ],
 | 
			
		||||
        child: const Main(),
 | 
			
		||||
      )
 | 
			
		||||
 
 | 
			
		||||
@@ -0,0 +1,9 @@
 | 
			
		||||
import 'package:flutter/material.dart';
 | 
			
		||||
 | 
			
		||||
import 'models/subject.dart';
 | 
			
		||||
 | 
			
		||||
abstract class AbiturCalculatorStep extends Step {
 | 
			
		||||
  const AbiturCalculatorStep({required super.title, required super.content});
 | 
			
		||||
 | 
			
		||||
  bool canGoNextStep(SubjectCollection subjects);
 | 
			
		||||
}
 | 
			
		||||
@@ -0,0 +1,89 @@
 | 
			
		||||
import 'package:flutter/material.dart';
 | 
			
		||||
import '../../../../widget/confirmDialog.dart';
 | 
			
		||||
import 'models/abiturCalculatorModel.dart';
 | 
			
		||||
import 'models/subject.dart';
 | 
			
		||||
import 'package:provider/provider.dart';
 | 
			
		||||
 | 
			
		||||
class AbiturCalculatorView extends StatelessWidget {
 | 
			
		||||
  const AbiturCalculatorView({super.key});
 | 
			
		||||
 | 
			
		||||
  static RichText listSubjects(List<Subject> subjects) {
 | 
			
		||||
    return RichText(
 | 
			
		||||
      textAlign: TextAlign.center,
 | 
			
		||||
      text: TextSpan(
 | 
			
		||||
        children: subjects.map((subject) {
 | 
			
		||||
          return List<InlineSpan>.from([
 | 
			
		||||
            WidgetSpan(child: Icon(subject.icon, size: 15)),
 | 
			
		||||
            const WidgetSpan(child: SizedBox(width: 3)),
 | 
			
		||||
            TextSpan(text: subject.displayName),
 | 
			
		||||
            if(subjects.last != subject) const WidgetSpan(child: SizedBox(width: 10)),
 | 
			
		||||
          ]);
 | 
			
		||||
        }).expand((e) => e).toList(),
 | 
			
		||||
      ),
 | 
			
		||||
    );
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  @override
 | 
			
		||||
  Widget build(BuildContext context) {
 | 
			
		||||
    return Consumer<AbiturCalculatorModel>(builder: (context, state, child) {
 | 
			
		||||
      return Scaffold(
 | 
			
		||||
          appBar: AppBar(
 | 
			
		||||
            title: const Text('Abitur Notenrechner'),
 | 
			
		||||
            actions: [
 | 
			
		||||
              IconButton(
 | 
			
		||||
                onPressed: () => ConfirmDialog(
 | 
			
		||||
                  title: 'Zurücksetzen',
 | 
			
		||||
                  content: 'Alle Felder werden zurückgesetzt',
 | 
			
		||||
                  confirmButton: 'Löschen',
 | 
			
		||||
                  onConfirm: state.reset,
 | 
			
		||||
                ).asDialog(context),
 | 
			
		||||
                icon: const Icon(Icons.delete_outline_outlined),
 | 
			
		||||
              )
 | 
			
		||||
            ],
 | 
			
		||||
          ),
 | 
			
		||||
          body: Stepper(
 | 
			
		||||
            type: StepperType.vertical,
 | 
			
		||||
            steps: state.getSteps,
 | 
			
		||||
            currentStep: state.getCurrentStepIndex,
 | 
			
		||||
 | 
			
		||||
            onStepContinue: () => state.increaseStep(),
 | 
			
		||||
            onStepCancel: () => state.decreaseStep(),
 | 
			
		||||
 | 
			
		||||
            stepIconBuilder: (stepIndex, stepState) => _stepIconBuilder(context, stepIndex, stepState),
 | 
			
		||||
            controlsBuilder: _controlsBuilder,
 | 
			
		||||
          )
 | 
			
		||||
      );
 | 
			
		||||
    });
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  Widget _stepIconBuilder(BuildContext context, int stepIndex, StepState stepState) {
 | 
			
		||||
    return Consumer<AbiturCalculatorModel>(builder: (context, state, child) {
 | 
			
		||||
      return Container(
 | 
			
		||||
        decoration: BoxDecoration(
 | 
			
		||||
          borderRadius: BorderRadius.circular(20),
 | 
			
		||||
          color: state.getCurrentStepIndex == stepIndex
 | 
			
		||||
              ? Theme.of(context).primaryColor
 | 
			
		||||
              : Theme.of(context).colorScheme.surfaceVariant,
 | 
			
		||||
        ),
 | 
			
		||||
        child: Center(
 | 
			
		||||
          child: Text((++stepIndex).toString()),
 | 
			
		||||
        ),
 | 
			
		||||
      );
 | 
			
		||||
    });
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  Widget _controlsBuilder(BuildContext context, ControlsDetails details) {
 | 
			
		||||
    return Row(
 | 
			
		||||
      children: [
 | 
			
		||||
        TextButton(
 | 
			
		||||
          onPressed: details.onStepCancel,
 | 
			
		||||
          child: const Text('Zurück'),
 | 
			
		||||
        ),
 | 
			
		||||
        TextButton(
 | 
			
		||||
          onPressed: details.onStepContinue,
 | 
			
		||||
          child: const Text('Weiter'),
 | 
			
		||||
        ),
 | 
			
		||||
      ]
 | 
			
		||||
    );
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
@@ -0,0 +1,81 @@
 | 
			
		||||
import 'package:flutter/material.dart';
 | 
			
		||||
import 'package:provider/provider.dart';
 | 
			
		||||
 | 
			
		||||
import '../abiturCalculatorStep.dart';
 | 
			
		||||
import '../steps/resultStep.dart';
 | 
			
		||||
import '../steps/selectGkStep.dart';
 | 
			
		||||
import '../steps/selectLkStep.dart';
 | 
			
		||||
import '../steps/selectPfStep.dart';
 | 
			
		||||
import '../steps/welcomeStep.dart';
 | 
			
		||||
import 'subject.dart';
 | 
			
		||||
 | 
			
		||||
class AbiturCalculatorModel extends ChangeNotifier {
 | 
			
		||||
  static final SubjectCollection _collection = SubjectCollection([
 | 
			
		||||
    Subject(displayName: 'Deutsch', icon: Icons.translate_outlined, canBeLk: true, importantLk: true),
 | 
			
		||||
    Subject(displayName: 'Erste Fremdsprache', icon: Icons.translate_outlined, canBeLk: true, importantLk: true),
 | 
			
		||||
    Subject(displayName: 'Zweite Fremdsprache', icon: Icons.translate_outlined, canBeLk: true, importantLk: true),
 | 
			
		||||
    Subject(displayName: 'Zweite Fremdsprache ab Kl. 11', icon: Icons.translate_outlined, canBeLk: false, importantLk: false),
 | 
			
		||||
    Subject(displayName: 'Kunst', icon: Icons.brush_outlined, canBeLk: true, importantLk: false),
 | 
			
		||||
    Subject(displayName: 'Musik', icon: Icons.music_note_outlined, canBeLk: true, importantLk: false),
 | 
			
		||||
    Subject(displayName: 'Darstellendes Spiel', icon: Icons.theater_comedy_outlined, canBeLk: false, importantLk: false),
 | 
			
		||||
    Subject(displayName: 'PoWi', icon: Icons.book_outlined, canBeLk: true, importantLk: false),
 | 
			
		||||
    Subject(displayName: 'Geschichte', icon: Icons.history_outlined, canBeLk: true, importantLk: false),
 | 
			
		||||
    Subject(displayName: 'Religion', icon: Icons.church_outlined, canBeLk: true, importantLk: false),
 | 
			
		||||
    Subject(displayName: 'Erdkunde', icon: Icons.map_outlined, canBeLk: true, importantLk: false),
 | 
			
		||||
    Subject(displayName: 'Mathematik', icon: Icons.calculate_outlined, canBeLk: true, importantLk: true),
 | 
			
		||||
    Subject(displayName: 'Chemie', icon: Icons.science_outlined, canBeLk: true, importantLk: true),
 | 
			
		||||
    Subject(displayName: 'Physik', icon: Icons.add, canBeLk: true, importantLk: true),
 | 
			
		||||
    Subject(displayName: 'Biologie', icon: Icons.add, canBeLk: true, importantLk: true),
 | 
			
		||||
    Subject(displayName: 'Biochemie', icon: Icons.biotech_outlined, canBeLk: false, importantLk: false),
 | 
			
		||||
    Subject(displayName: 'Informatik', icon: Icons.code_outlined, canBeLk: true, importantLk: false),
 | 
			
		||||
    Subject(displayName: 'Sport', icon: Icons.sports_basketball_outlined, canBeLk: true, importantLk: false),
 | 
			
		||||
  ]);
 | 
			
		||||
 | 
			
		||||
  static final List<AbiturCalculatorStep> _steps = [
 | 
			
		||||
    const WelcomeStep(),
 | 
			
		||||
    SelectLkStep(),
 | 
			
		||||
    SelectGkStep(),
 | 
			
		||||
    const SelectPfStep(),
 | 
			
		||||
    const ResultStep(),
 | 
			
		||||
  ];
 | 
			
		||||
  
 | 
			
		||||
  List<AbiturCalculatorStep> get getSteps => _steps;
 | 
			
		||||
  AbiturCalculatorStep getCurrentStep() => _steps[getCurrentStepIndex];
 | 
			
		||||
 | 
			
		||||
  static AbiturCalculatorModel get(BuildContext context) {
 | 
			
		||||
    return Provider.of<AbiturCalculatorModel>(context, listen: false);
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  int _currentStep = 0;
 | 
			
		||||
 | 
			
		||||
  SubjectCollection getSubjects({bool update = false}) {
 | 
			
		||||
    if(update) notifyListeners();
 | 
			
		||||
    return _collection;
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  void update() {
 | 
			
		||||
    notifyListeners();
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  int get getCurrentStepIndex => _currentStep;
 | 
			
		||||
  void increaseStep() {
 | 
			
		||||
    if(getCurrentStep().canGoNextStep(getSubjects())) _currentStep++;
 | 
			
		||||
    notifyListeners();
 | 
			
		||||
  }
 | 
			
		||||
  void decreaseStep() {
 | 
			
		||||
    if(_currentStep >= 1) _currentStep--;
 | 
			
		||||
    notifyListeners();
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  void reset() {
 | 
			
		||||
    _currentStep = 0;
 | 
			
		||||
    for (var e in _collection.collection) {
 | 
			
		||||
      e.reset();
 | 
			
		||||
    }
 | 
			
		||||
    notifyListeners();
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  AbiturCalculatorModel() {
 | 
			
		||||
    reset();
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										61
									
								
								lib/view/pages/more/abiturCalculator/models/subject.dart
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										61
									
								
								lib/view/pages/more/abiturCalculator/models/subject.dart
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,61 @@
 | 
			
		||||
import 'package:flutter/cupertino.dart';
 | 
			
		||||
import 'package:flutter/material.dart';
 | 
			
		||||
 | 
			
		||||
enum SubjectState {
 | 
			
		||||
  none,
 | 
			
		||||
  isLk,
 | 
			
		||||
  isGk,
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
class HighEduGraduationConstants {
 | 
			
		||||
  static const int maxLks = 2;
 | 
			
		||||
  static const int maxGks = 9;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
class SubjectCollection {
 | 
			
		||||
  List<Subject> collection;
 | 
			
		||||
 | 
			
		||||
  SubjectCollection(this.collection);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
class Subject {
 | 
			
		||||
  final String displayName;
 | 
			
		||||
  final IconData icon;
 | 
			
		||||
  final bool canBeLk;
 | 
			
		||||
  final bool importantLk;
 | 
			
		||||
 | 
			
		||||
  SubjectState _subjectState = SubjectState.none;
 | 
			
		||||
 | 
			
		||||
  bool isLk() => _subjectState == SubjectState.isLk;
 | 
			
		||||
  bool isGk() => _subjectState == SubjectState.isGk;
 | 
			
		||||
 | 
			
		||||
  bool canLk(List<Subject> other) {
 | 
			
		||||
    Subject? otherLk() => other.where((s) => s.isLk()).firstOrNull;
 | 
			
		||||
    bool hasOtherLk() => otherLk() != null;
 | 
			
		||||
 | 
			
		||||
    return
 | 
			
		||||
      ((hasOtherLk() && otherLk()!.importantLk) || importantLk)
 | 
			
		||||
      && canBeLk
 | 
			
		||||
      && !isGk()
 | 
			
		||||
      && other.where((s) => s.isLk()).length < HighEduGraduationConstants.maxLks;
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  bool canGk(List<Subject> other) => !isLk() && other.where((s) => s.isGk()).length < HighEduGraduationConstants.maxGks;
 | 
			
		||||
 | 
			
		||||
  set unsafeSubjectSet(SubjectState newState) => _subjectState = newState;
 | 
			
		||||
  set unsafeLkToggle(bool isLk) {
 | 
			
		||||
    if(isLk) {
 | 
			
		||||
 | 
			
		||||
    }
 | 
			
		||||
    _subjectState = isLk ? SubjectState.isLk : SubjectState.none;
 | 
			
		||||
  }
 | 
			
		||||
  set unsafeGkToggle(bool isGk) {
 | 
			
		||||
    _subjectState = isGk ? SubjectState.isGk : SubjectState.none;
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  void reset() {
 | 
			
		||||
    _subjectState = SubjectState.none;
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  Subject({required this.displayName, required this.icon, required this.canBeLk, required this.importantLk});
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										16
									
								
								lib/view/pages/more/abiturCalculator/notes.md
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										16
									
								
								lib/view/pages/more/abiturCalculator/notes.md
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,16 @@
 | 
			
		||||
Standart auswahl nach LK änderung
 | 
			
		||||
 | 
			
		||||
Deutsch
 | 
			
		||||
Erste Fremdsprache
 | 
			
		||||
Powi
 | 
			
		||||
Geschichte
 | 
			
		||||
Religion
 | 
			
		||||
Mathe
 | 
			
		||||
Sport
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
Kunst
 | 
			
		||||
Musik
 | 
			
		||||
DS
 | 
			
		||||
Exklusiv -> Nur eins der 3 wählbar
 | 
			
		||||
Plichtgruppe -> EIns der drei muss gewählt sein (nur bei den Grundkursen)
 | 
			
		||||
							
								
								
									
										16
									
								
								lib/view/pages/more/abiturCalculator/steps/resultStep.dart
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										16
									
								
								lib/view/pages/more/abiturCalculator/steps/resultStep.dart
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,16 @@
 | 
			
		||||
import 'package:flutter/material.dart';
 | 
			
		||||
 | 
			
		||||
import '../abiturCalculatorStep.dart';
 | 
			
		||||
import '../models/subject.dart';
 | 
			
		||||
 | 
			
		||||
class ResultStep extends AbiturCalculatorStep {
 | 
			
		||||
  const ResultStep() : super(
 | 
			
		||||
    title: const Text('Ergebnis'),
 | 
			
		||||
    content: const SizedBox.shrink(),
 | 
			
		||||
  );
 | 
			
		||||
 | 
			
		||||
  @override
 | 
			
		||||
  bool canGoNextStep(SubjectCollection subjects) {
 | 
			
		||||
    throw UnimplementedError();
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										66
									
								
								lib/view/pages/more/abiturCalculator/steps/selectGkStep.dart
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										66
									
								
								lib/view/pages/more/abiturCalculator/steps/selectGkStep.dart
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,66 @@
 | 
			
		||||
import 'package:flutter/material.dart';
 | 
			
		||||
import '../../../../../widget/centeredLeading.dart';
 | 
			
		||||
import '../../../../../widget/providerBridge.dart';
 | 
			
		||||
import '../abiturCalculatorStep.dart';
 | 
			
		||||
import '../abiturCalculatorView.dart';
 | 
			
		||||
 | 
			
		||||
import '../models/abiturCalculatorModel.dart';
 | 
			
		||||
import '../models/subject.dart';
 | 
			
		||||
 | 
			
		||||
class SelectGkStep extends AbiturCalculatorStep {
 | 
			
		||||
  SelectGkStep() : super(
 | 
			
		||||
    title: const Text('Grundkurse'),
 | 
			
		||||
    content: Builder(builder: (context) {
 | 
			
		||||
      var model = AbiturCalculatorModel.get(context);
 | 
			
		||||
      var gkSubjects = model.getSubjects().collection.where((e) => e.isGk()).toList();
 | 
			
		||||
      return Column(
 | 
			
		||||
        children: [
 | 
			
		||||
          AbiturCalculatorView.listSubjects(gkSubjects),
 | 
			
		||||
          TextButton(
 | 
			
		||||
            onPressed: () {
 | 
			
		||||
              ProviderBridge.toDialog(context, model, (context, value) {
 | 
			
		||||
                return AlertDialog(
 | 
			
		||||
                  title: const Text('Grundkurse'),
 | 
			
		||||
                  content: SingleChildScrollView(
 | 
			
		||||
                    child: Column(
 | 
			
		||||
                      mainAxisSize: MainAxisSize.min,
 | 
			
		||||
                      children: model.getSubjects().collection.map((e) {
 | 
			
		||||
                        return ListTile(
 | 
			
		||||
                          leading: CenteredLeading(Icon(e.icon)),
 | 
			
		||||
                          title: Text(e.displayName),
 | 
			
		||||
                          trailing: Checkbox(
 | 
			
		||||
                            value: e.isGk(),
 | 
			
		||||
                            onChanged: e.isGk() || e.canGk(model.getSubjects().collection) ? (value) {
 | 
			
		||||
                              e.unsafeGkToggle = value!;
 | 
			
		||||
                              model.update();
 | 
			
		||||
                            } : null,
 | 
			
		||||
                          ),
 | 
			
		||||
                        );
 | 
			
		||||
                      }).toList(),
 | 
			
		||||
                    ),
 | 
			
		||||
                  ),
 | 
			
		||||
                  actions: [
 | 
			
		||||
                    TextButton(
 | 
			
		||||
                      onPressed: () {
 | 
			
		||||
                        Navigator.of(context).pop();
 | 
			
		||||
                      },
 | 
			
		||||
                      child: const Text('Fertig'),
 | 
			
		||||
                    )
 | 
			
		||||
                  ],
 | 
			
		||||
                );
 | 
			
		||||
              });
 | 
			
		||||
            },
 | 
			
		||||
            child: Text(
 | 
			
		||||
                "Grundkurse ${gkSubjects.isEmpty ? "auswählen" : "ändern"}"),
 | 
			
		||||
          ),
 | 
			
		||||
        ],
 | 
			
		||||
      );
 | 
			
		||||
    }),
 | 
			
		||||
  );
 | 
			
		||||
 | 
			
		||||
  @override
 | 
			
		||||
  bool canGoNextStep(SubjectCollection subjects) {
 | 
			
		||||
    // TODO: implement canGoNextStepp
 | 
			
		||||
    throw UnimplementedError();
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										72
									
								
								lib/view/pages/more/abiturCalculator/steps/selectLkStep.dart
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										72
									
								
								lib/view/pages/more/abiturCalculator/steps/selectLkStep.dart
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,72 @@
 | 
			
		||||
import 'package:flutter/material.dart';
 | 
			
		||||
import '../../../../../widget/providerBridge.dart';
 | 
			
		||||
 | 
			
		||||
import '../../../../../widget/centeredLeading.dart';
 | 
			
		||||
import '../abiturCalculatorStep.dart';
 | 
			
		||||
import '../abiturCalculatorView.dart';
 | 
			
		||||
import '../models/abiturCalculatorModel.dart';
 | 
			
		||||
import '../models/subject.dart';
 | 
			
		||||
 | 
			
		||||
class SelectLkStep extends AbiturCalculatorStep {
 | 
			
		||||
  SelectLkStep() : super(
 | 
			
		||||
    title: const Text('Leistungskurse'),
 | 
			
		||||
    content: StatefulBuilder(builder: (context, setState) {
 | 
			
		||||
      var model = AbiturCalculatorModel.get(context);
 | 
			
		||||
      var lkSubjects = model.getSubjects().collection.where((e) => e.isLk()).toList();
 | 
			
		||||
      return Column(
 | 
			
		||||
        children: [
 | 
			
		||||
          AbiturCalculatorView.listSubjects(lkSubjects),
 | 
			
		||||
          TextButton(
 | 
			
		||||
            onPressed: () {
 | 
			
		||||
              ProviderBridge.toDialog(context, model, (context, value) {
 | 
			
		||||
                return AlertDialog(
 | 
			
		||||
                  title: const Text('Leistungskurse'),
 | 
			
		||||
                  content: SingleChildScrollView(
 | 
			
		||||
                    child: Column(
 | 
			
		||||
                      mainAxisSize: MainAxisSize.min,
 | 
			
		||||
                      children: model.getSubjects().collection.map((e) {
 | 
			
		||||
                        return ListTile(
 | 
			
		||||
                          leading: CenteredLeading(Icon(e.icon)),
 | 
			
		||||
                          title: Text(e.displayName),
 | 
			
		||||
                          trailing: Checkbox(
 | 
			
		||||
                            value: e.isLk(),
 | 
			
		||||
                            onChanged: e.isLk() || e.canLk(model.getSubjects().collection) ? (value) {
 | 
			
		||||
                              e.unsafeLkToggle = value!;
 | 
			
		||||
                              model.update();
 | 
			
		||||
                            } : null,
 | 
			
		||||
                          ),
 | 
			
		||||
                        );
 | 
			
		||||
                      }).toList(),
 | 
			
		||||
                    ),
 | 
			
		||||
                  ),
 | 
			
		||||
                  actions: [
 | 
			
		||||
                    TextButton(
 | 
			
		||||
                      onPressed: () {
 | 
			
		||||
                        Navigator.of(context).pop();
 | 
			
		||||
                      },
 | 
			
		||||
                      child: const Text('Fertig'),
 | 
			
		||||
                    )
 | 
			
		||||
                  ],
 | 
			
		||||
                );
 | 
			
		||||
              });
 | 
			
		||||
            },
 | 
			
		||||
            child: Text("Leistungskurse ${lkSubjects.isEmpty ? "auswählen" : "ändern"}"),
 | 
			
		||||
          ),
 | 
			
		||||
        ],
 | 
			
		||||
      );
 | 
			
		||||
    }),
 | 
			
		||||
  );
 | 
			
		||||
 | 
			
		||||
  @override
 | 
			
		||||
  bool canGoNextStep(SubjectCollection subjects) {
 | 
			
		||||
    return subjects.collection.where((element) => element.isLk()).length >= 2;
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
class SelectLkStepTest extends StatelessWidget {
 | 
			
		||||
  const SelectLkStepTest({super.key});
 | 
			
		||||
 | 
			
		||||
  @override
 | 
			
		||||
  Widget build(BuildContext context) {
 | 
			
		||||
    return const Placeholder();
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										17
									
								
								lib/view/pages/more/abiturCalculator/steps/selectPfStep.dart
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										17
									
								
								lib/view/pages/more/abiturCalculator/steps/selectPfStep.dart
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,17 @@
 | 
			
		||||
import 'package:flutter/material.dart';
 | 
			
		||||
 | 
			
		||||
import '../abiturCalculatorStep.dart';
 | 
			
		||||
import '../models/subject.dart';
 | 
			
		||||
 | 
			
		||||
class SelectPfStep extends AbiturCalculatorStep {
 | 
			
		||||
  const SelectPfStep() : super(
 | 
			
		||||
    title: const Text('Prüfungsfächer'),
 | 
			
		||||
    content: const SizedBox.shrink(),
 | 
			
		||||
  );
 | 
			
		||||
 | 
			
		||||
  @override
 | 
			
		||||
  bool canGoNextStep(SubjectCollection subjects) {
 | 
			
		||||
    // TODO: implement canGoNextStepp
 | 
			
		||||
    throw UnimplementedError();
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
							
								
								
									
										16
									
								
								lib/view/pages/more/abiturCalculator/steps/welcomeStep.dart
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										16
									
								
								lib/view/pages/more/abiturCalculator/steps/welcomeStep.dart
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,16 @@
 | 
			
		||||
import 'package:flutter/material.dart';
 | 
			
		||||
 | 
			
		||||
import '../abiturCalculatorStep.dart';
 | 
			
		||||
import '../models/subject.dart';
 | 
			
		||||
 | 
			
		||||
class WelcomeStep extends AbiturCalculatorStep {
 | 
			
		||||
  const WelcomeStep() : super(
 | 
			
		||||
      title: const Text('Willkommen'),
 | 
			
		||||
      content: const Text('In den folgenden Schritten werden alle nötigen Informationen zur Ermittlung deiner Abiturzulassung abgefragt.')
 | 
			
		||||
  );
 | 
			
		||||
 | 
			
		||||
  @override
 | 
			
		||||
  bool canGoNextStep(SubjectCollection subjects) {
 | 
			
		||||
    return true;
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
@@ -10,6 +10,7 @@ import '../../widget/ListItem.dart';
 | 
			
		||||
import '../../widget/centeredLeading.dart';
 | 
			
		||||
import '../../widget/infoDialog.dart';
 | 
			
		||||
import '../settings/settings.dart';
 | 
			
		||||
import 'more/abiturCalculator/abiturCalculatorView.dart';
 | 
			
		||||
import 'more/feedback/feedbackDialog.dart';
 | 
			
		||||
import 'more/gradeAverages/gradeAverage.dart';
 | 
			
		||||
import 'more/holidays/holidays.dart';
 | 
			
		||||
@@ -35,6 +36,7 @@ class Overhang extends StatelessWidget {
 | 
			
		||||
          const ListItemNavigator(icon: Icons.newspaper, text: 'Marianum Message', target: Message()),
 | 
			
		||||
          const ListItemNavigator(icon: Icons.room, text: 'Raumplan', target: Roomplan()),
 | 
			
		||||
          const ListItemNavigator(icon: Icons.calculate, text: 'Notendurschnittsrechner', target: GradeAverage()),
 | 
			
		||||
          const ListItemNavigator(icon: Icons.school_outlined, text: 'Abiturrechner', target: AbiturCalculatorView()),
 | 
			
		||||
          const ListItemNavigator(icon: Icons.calendar_month, text: 'Schulferien', target: Holidays()),
 | 
			
		||||
          const Divider(),
 | 
			
		||||
          ListTile(
 | 
			
		||||
 
 | 
			
		||||
							
								
								
									
										19
									
								
								lib/widget/providerBridge.dart
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										19
									
								
								lib/widget/providerBridge.dart
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,19 @@
 | 
			
		||||
import 'package:flutter/material.dart';
 | 
			
		||||
import 'package:provider/provider.dart';
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
class ProviderBridge {
 | 
			
		||||
  static void toDialog<T extends ChangeNotifier>(BuildContext context, T data, Widget Function(BuildContext context, T value) builder) {
 | 
			
		||||
    showDialog(
 | 
			
		||||
      context: context,
 | 
			
		||||
      builder: (context) {
 | 
			
		||||
        return ChangeNotifierProvider.value(
 | 
			
		||||
          value: data,
 | 
			
		||||
          builder: (context, child) {
 | 
			
		||||
            return Consumer<T>(builder: (context, value, child) => builder(context, value));
 | 
			
		||||
          },
 | 
			
		||||
        );
 | 
			
		||||
      },
 | 
			
		||||
    );
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
		Reference in New Issue
	
	Block a user