Merge pull request 'mcy_new' (#1) from mcy_new into master

Reviewed-on: #1
This commit is contained in:
wangyang 2025-08-28 10:10:44 +08:00
commit 5f4c9237c1
699 changed files with 22859 additions and 9059 deletions

61
.gitignore vendored
View File

@ -3,20 +3,18 @@
*.log
*.pyc
*.swp
.DS_Store
.atom/
.buildlog/
.history
.svn/
migrate_working_dir/
**/.DS_Store
**/.atom/
**/.buildlog/
**/.history
**/.svn/
**/migrate_working_dir/
# IntelliJ related
*.iml
*.ipr
*.iws
.idea/
# 编译文件不上传
*.g.dart
# The .vscode folder contains launch configuration and tasks you configure in
@ -27,13 +25,13 @@ migrate_working_dir/
# Flutter/Dart/Pub related
**/doc/api/
**/ios/Flutter/.last_build_id
.dart_tool/
.flutter-plugins
.flutter-plugins-dependencies
.packages
.pub-cache/
.pub/
/build/
**/.dart_tool/
**/.flutter-plugins
**/.flutter-plugins-dependencies
**/.pub-cache/
**/.pub/
**/build/
**/lib/*.g.dart
# Symbolication related
app.*.symbols
@ -42,21 +40,18 @@ app.*.symbols
app.*.map.json
# Android Studio will place build artifacts here
/android/app/debug
/android/app/profile
/android/app/release
/.fvm/flutter_sdk
lib/common/api/retrofit_client.g.dart
lib/common/job/user_info.g.dart
lib/common/job/user_info.g.dart
lib/common/job/user_login.g.dart
lib/common/job/common/upload_img_secret_key.g.dart
lib/common/job/common/base_structure_result.g.dart
lib/common/job/common/base_page.g.dart
lib/common/job/common/base_page_report.g.dart
lib/common/job/common/base_page_data.g.dart
lib/common/job/common/base_page_data_report.g.dart
/.fvm/flutter_sdk
.fvm/fvm_config.json
pubspec.lock
pubspec.lock
**/android/app/debug
**/android/app/profile
**/android/app/release
making_school_asignment_app/*.g.dart
making_school_asignment_app/pubspec.lock
making_school_asignment_app/lib/common/api/retrofit_client.g.dart
making_school_asignment_app/lib/page/home_page/children/read_over/read_over_view.g.dart
making_school_asignment_app/lib/page/home_page/children/read_over/read_over_view.g.dart
making_school_asignment_app/lib/page/home_page/children/read_over/read_over_view.g.dart
making_school_asignment_app/lib/common/api/retrofit_client.g.dart
making_school_asignment_app/lib/page/home_page/children/read_over/read_over_view.g.dart
.vscode/settings.json
.vscode/launch.json
making_school_asignment_app/.fvm/fvm_config.json
making_school_asignment_app/.fvm/flutter_sdk

View File

@ -1,33 +0,0 @@
# This file tracks properties of this Flutter project.
# Used by Flutter tool to assess capabilities and perform upgrades etc.
#
# This file should be version controlled.
version:
revision: d3d8effc686d73e0114d71abdcccef63fa1f25d2
channel: stable
project_type: app
# Tracks metadata for the flutter migrate command
migration:
platforms:
- platform: root
create_revision: d3d8effc686d73e0114d71abdcccef63fa1f25d2
base_revision: d3d8effc686d73e0114d71abdcccef63fa1f25d2
- platform: android
create_revision: d3d8effc686d73e0114d71abdcccef63fa1f25d2
base_revision: d3d8effc686d73e0114d71abdcccef63fa1f25d2
- platform: ios
create_revision: d3d8effc686d73e0114d71abdcccef63fa1f25d2
base_revision: d3d8effc686d73e0114d71abdcccef63fa1f25d2
# User provided section
# List of Local paths (relative to this file) that should be
# ignored by the migrate tool.
#
# Files that are not part of the templates will be ignored by default.
unmanaged_files:
- 'lib/main.dart'
- 'ios/Runner.xcodeproj/project.pbxproj'

View File

@ -1,73 +0,0 @@
def localProperties = new Properties()
def localPropertiesFile = rootProject.file('local.properties')
if (localPropertiesFile.exists()) {
localPropertiesFile.withReader('UTF-8') { reader ->
localProperties.load(reader)
}
}
def flutterRoot = localProperties.getProperty('flutter.sdk')
if (flutterRoot == null) {
throw new GradleException("Flutter SDK not found. Define location with flutter.sdk in the local.properties file.")
}
def flutterVersionCode = localProperties.getProperty('flutter.versionCode')
if (flutterVersionCode == null) {
flutterVersionCode = '1'
}
def flutterVersionName = localProperties.getProperty('flutter.versionName')
if (flutterVersionName == null) {
flutterVersionName = '1.0'
}
apply plugin: 'com.android.application'
apply plugin: 'kotlin-android'
apply from: "$flutterRoot/packages/flutter_tools/gradle/flutter.gradle"
android {
namespace "com.example.school_asignment_app"
compileSdkVersion flutter.compileSdkVersion
ndkVersion flutter.ndkVersion
compileOptions {
sourceCompatibility JavaVersion.VERSION_1_8
targetCompatibility JavaVersion.VERSION_1_8
}
kotlinOptions {
jvmTarget = '1.8'
}
sourceSets {
main.java.srcDirs += 'src/main/kotlin'
}
defaultConfig {
// TODO: Specify your own unique Application ID (https://developer.android.com/studio/build/application-id.html).
applicationId "com.example.school_asignment_app"
// You can update the following values to match your application needs.
// For more information, see: https://docs.flutter.dev/deployment/android#reviewing-the-gradle-build-configuration.
// minSdkVersion flutter.minSdkVersion
minSdkVersion 21
targetSdkVersion flutter.targetSdkVersion
versionCode flutterVersionCode.toInteger()
versionName flutterVersionName
}
buildTypes {
release {
// TODO: Add your own signing config for the release build.
// Signing with the debug keys for now, so `flutter run --release` works.
signingConfig signingConfigs.debug
}
}
}
flutter {
source '../..'
}
dependencies {
implementation "org.jetbrains.kotlin:kotlin-stdlib-jdk7:$kotlin_version"
}

View File

@ -1,33 +0,0 @@
<manifest xmlns:android="http://schemas.android.com/apk/res/android">
<application
android:label="school_asignment_app"
android:name="${applicationName}"
android:icon="@mipmap/ic_launcher">
<activity
android:name=".MainActivity"
android:exported="true"
android:launchMode="singleTop"
android:theme="@style/LaunchTheme"
android:configChanges="orientation|keyboardHidden|keyboard|screenSize|smallestScreenSize|locale|layoutDirection|fontScale|screenLayout|density|uiMode"
android:hardwareAccelerated="true"
android:windowSoftInputMode="adjustResize">
<!-- Specifies an Android theme to apply to this Activity as soon as
the Android process has started. This theme is visible to the user
while the Flutter UI initializes. After that, this theme continues
to determine the Window background behind the Flutter UI. -->
<meta-data
android:name="io.flutter.embedding.android.NormalTheme"
android:resource="@style/NormalTheme"
/>
<intent-filter>
<action android:name="android.intent.action.MAIN"/>
<category android:name="android.intent.category.LAUNCHER"/>
</intent-filter>
</activity>
<!-- Don't delete the meta-data below.
This is used by the Flutter tool to generate GeneratedPluginRegistrant.java -->
<meta-data
android:name="flutterEmbedding"
android:value="2" />
</application>
</manifest>

View File

@ -1,6 +0,0 @@
package com.example.school_asignment_app
import io.flutter.embedding.android.FlutterActivity
class MainActivity: FlutterActivity() {
}

View File

@ -1,12 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Modify this file to customize your launch splash screen -->
<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
<item android:drawable="?android:colorBackground" />
<!-- You can insert your own image assets here -->
<!-- <item>
<bitmap
android:gravity="center"
android:src="@mipmap/launch_image" />
</item> -->
</layer-list>

View File

@ -1,12 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Modify this file to customize your launch splash screen -->
<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
<item android:drawable="@android:color/white" />
<!-- You can insert your own image assets here -->
<!-- <item>
<bitmap
android:gravity="center"
android:src="@mipmap/launch_image" />
</item> -->
</layer-list>

Binary file not shown.

Before

Width:  |  Height:  |  Size: 544 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 442 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 721 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.0 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.4 KiB

View File

@ -1,7 +0,0 @@
<manifest xmlns:android="http://schemas.android.com/apk/res/android">
<!-- The INTERNET permission is required for development. Specifically,
the Flutter tool needs it to communicate with the running application
to allow setting breakpoints, to provide hot reload, etc.
-->
<uses-permission android:name="android.permission.INTERNET"/>
</manifest>

View File

@ -1,31 +0,0 @@
buildscript {
ext.kotlin_version = '1.7.10'
repositories {
google()
mavenCentral()
}
dependencies {
classpath 'com.android.tools.build:gradle:7.3.0'
classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlin_version"
}
}
allprojects {
repositories {
google()
mavenCentral()
}
}
rootProject.buildDir = '../build'
subprojects {
project.buildDir = "${rootProject.buildDir}/${project.name}"
}
subprojects {
project.evaluationDependsOn(':app')
}
tasks.register("clean", Delete) {
delete rootProject.buildDir
}

View File

@ -1,3 +0,0 @@
org.gradle.jvmargs=-Xmx1536M
android.useAndroidX=true
android.enableJetifier=true

View File

@ -1,11 +0,0 @@
include ':app'
def localPropertiesFile = new File(rootProject.projectDir, "local.properties")
def properties = new Properties()
assert localPropertiesFile.exists()
localPropertiesFile.withReader("UTF-8") { reader -> properties.load(reader) }
def flutterSdkPath = properties.getProperty("flutter.sdk")
assert flutterSdkPath != null, "flutter.sdk not set in local.properties"
apply from: "$flutterSdkPath/packages/flutter_tools/gradle/app_plugin_loader.gradle"

File diff suppressed because one or more lines are too long

Binary file not shown.

Binary file not shown.

Binary file not shown.

Before

Width:  |  Height:  |  Size: 886 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.8 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.2 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.9 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 857 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 2.7 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 105 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 15 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 112 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.2 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 3.2 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.7 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 3.2 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.1 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 5.0 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 200 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 26 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 177 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.6 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 4.8 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 2.2 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 4.9 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.4 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 7.9 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 296 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 38 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 140 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 790 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 546 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.7 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 942 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.2 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.3 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.8 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 303 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 326 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.8 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 544 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 292 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 40 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 468 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 833 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 26 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.2 KiB

View File

@ -1 +0,0 @@
#include "Generated.xcconfig"

View File

@ -1 +0,0 @@
#include "Generated.xcconfig"

View File

@ -1,122 +0,0 @@
{
"images" : [
{
"size" : "20x20",
"idiom" : "iphone",
"filename" : "Icon-App-20x20@2x.png",
"scale" : "2x"
},
{
"size" : "20x20",
"idiom" : "iphone",
"filename" : "Icon-App-20x20@3x.png",
"scale" : "3x"
},
{
"size" : "29x29",
"idiom" : "iphone",
"filename" : "Icon-App-29x29@1x.png",
"scale" : "1x"
},
{
"size" : "29x29",
"idiom" : "iphone",
"filename" : "Icon-App-29x29@2x.png",
"scale" : "2x"
},
{
"size" : "29x29",
"idiom" : "iphone",
"filename" : "Icon-App-29x29@3x.png",
"scale" : "3x"
},
{
"size" : "40x40",
"idiom" : "iphone",
"filename" : "Icon-App-40x40@2x.png",
"scale" : "2x"
},
{
"size" : "40x40",
"idiom" : "iphone",
"filename" : "Icon-App-40x40@3x.png",
"scale" : "3x"
},
{
"size" : "60x60",
"idiom" : "iphone",
"filename" : "Icon-App-60x60@2x.png",
"scale" : "2x"
},
{
"size" : "60x60",
"idiom" : "iphone",
"filename" : "Icon-App-60x60@3x.png",
"scale" : "3x"
},
{
"size" : "20x20",
"idiom" : "ipad",
"filename" : "Icon-App-20x20@1x.png",
"scale" : "1x"
},
{
"size" : "20x20",
"idiom" : "ipad",
"filename" : "Icon-App-20x20@2x.png",
"scale" : "2x"
},
{
"size" : "29x29",
"idiom" : "ipad",
"filename" : "Icon-App-29x29@1x.png",
"scale" : "1x"
},
{
"size" : "29x29",
"idiom" : "ipad",
"filename" : "Icon-App-29x29@2x.png",
"scale" : "2x"
},
{
"size" : "40x40",
"idiom" : "ipad",
"filename" : "Icon-App-40x40@1x.png",
"scale" : "1x"
},
{
"size" : "40x40",
"idiom" : "ipad",
"filename" : "Icon-App-40x40@2x.png",
"scale" : "2x"
},
{
"size" : "76x76",
"idiom" : "ipad",
"filename" : "Icon-App-76x76@1x.png",
"scale" : "1x"
},
{
"size" : "76x76",
"idiom" : "ipad",
"filename" : "Icon-App-76x76@2x.png",
"scale" : "2x"
},
{
"size" : "83.5x83.5",
"idiom" : "ipad",
"filename" : "Icon-App-83.5x83.5@2x.png",
"scale" : "2x"
},
{
"size" : "1024x1024",
"idiom" : "ios-marketing",
"filename" : "Icon-App-1024x1024@1x.png",
"scale" : "1x"
}
],
"info" : {
"version" : 1,
"author" : "xcode"
}
}

Binary file not shown.

Before

Width:  |  Height:  |  Size: 11 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 295 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 406 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 450 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 282 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 462 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 704 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 406 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 586 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 862 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 862 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.6 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 762 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.2 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.4 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 68 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 68 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 68 B

View File

@ -1,5 +0,0 @@
# Launch Screen Assets
You can customize the launch screen with your own desired assets by replacing the image files in this directory.
You can also do it by opening your Flutter project's Xcode project with `open ios/Runner.xcworkspace`, selecting `Runner/Assets.xcassets` in the Project Navigator and dropping in the desired images.

View File

@ -1,51 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>CFBundleDevelopmentRegion</key>
<string>$(DEVELOPMENT_LANGUAGE)</string>
<key>CFBundleDisplayName</key>
<string>School Asignment App</string>
<key>CFBundleExecutable</key>
<string>$(EXECUTABLE_NAME)</string>
<key>CFBundleIdentifier</key>
<string>$(PRODUCT_BUNDLE_IDENTIFIER)</string>
<key>CFBundleInfoDictionaryVersion</key>
<string>6.0</string>
<key>CFBundleName</key>
<string>school_asignment_app</string>
<key>CFBundlePackageType</key>
<string>APPL</string>
<key>CFBundleShortVersionString</key>
<string>$(FLUTTER_BUILD_NAME)</string>
<key>CFBundleSignature</key>
<string>????</string>
<key>CFBundleVersion</key>
<string>$(FLUTTER_BUILD_NUMBER)</string>
<key>LSRequiresIPhoneOS</key>
<true/>
<key>UILaunchStoryboardName</key>
<string>LaunchScreen</string>
<key>UIMainStoryboardFile</key>
<string>Main</string>
<key>UISupportedInterfaceOrientations</key>
<array>
<string>UIInterfaceOrientationPortrait</string>
<string>UIInterfaceOrientationLandscapeLeft</string>
<string>UIInterfaceOrientationLandscapeRight</string>
</array>
<key>UISupportedInterfaceOrientations~ipad</key>
<array>
<string>UIInterfaceOrientationPortrait</string>
<string>UIInterfaceOrientationPortraitUpsideDown</string>
<string>UIInterfaceOrientationLandscapeLeft</string>
<string>UIInterfaceOrientationLandscapeRight</string>
</array>
<key>UIViewControllerBasedStatusBarAppearance</key>
<false/>
<key>CADisableMinimumFrameDurationOnPhone</key>
<true/>
<key>UIApplicationSupportsIndirectInputEvents</key>
<true/>
</dict>
</plist>

View File

@ -1,101 +0,0 @@
import 'package:dio/dio.dart' hide Headers;
import 'package:retrofit/retrofit.dart';
import 'package:school_asignment_app/common/job/annotated_class.dart';
import 'package:school_asignment_app/common/job/class_item.dart';
import 'package:school_asignment_app/common/job/common/app_version_model.dart';
import 'package:school_asignment_app/common/job/common/base_app_version.dart';
import 'package:school_asignment_app/common/job/common/base_page_data.dart';
import 'package:school_asignment_app/common/job/enum_subject.dart';
import 'package:school_asignment_app/common/job/homework_details.dart';
import 'package:school_asignment_app/common/job/knowledge_points_grasp.dart';
import 'package:school_asignment_app/common/job/knowledge_report_detail.dart';
import 'package:school_asignment_app/common/job/student_history.dart';
import 'package:school_asignment_app/common/job/student_history_params.dart';
import 'package:school_asignment_app/common/job/student_item.dart';
import 'package:school_asignment_app/common/job/student_personal_info.dart';
import 'package:school_asignment_app/common/job/user_info_detail.dart';
import 'package:school_asignment_app/common/job/work_student.dart';
import 'package:school_asignment_app/common/job/work_student_params.dart';
part 'retrofit_client.g.dart';
@RestApi(parser: Parser.JsonSerializable)
@Headers(<String, dynamic>{"Content-Type": "application/json"})
abstract class RetrofitClient {
factory RetrofitClient(Dio dio, {String? baseUrl}) = _RetrofitClient;
/* start 系统系列接口 */
@POST("/api/infra/AppVersion/GetList")
Future<BasePageData<AppVersionModel>?> getAppVersions(@Body() BaseAppVersion appVersion);
/* start 系统系列接口 */
@POST("/api/rbac/Auth/DcLogin")
Future toLogin(@Field() String account, @Field() String password);
@GET("/api/rbac/User/GetUser")
Future<UserInfoDetail?> getUser(@Query('userId') String userId);
//
@GET("/api/hms/Homework/GetList")
Future<WorkStudent> getWorkList(@Queries() WorkStudentParams params);
//,
@GET("/api/app/Common/GetEnumInfos")
Future<Map<String, List<EnumSubject>>> getEnumSubjectList(@Query('enumNames') List enumNames);
//
@GET("/api/rbac/SchoolUser/GetTeacherClassSubject")
Future<List<ClassItem>> getStudentClass();
//
@GET("/api/rbac/Student/GetPriorityAnnotateStudents")
Future<List<StudentItem>> getStudentList(@Query('ClassId') String classId,@Query('Subject') int subject );
//
@GET("/api/hms/Annotate/GetUnAnnotateList")
Future<WorkStudent> getUnAnnotateList(@Queries() WorkStudentParams params);
//
@GET("/api/hms/Annotate/GetAnnotatedList")
Future<WorkStudent> getAnnotatedList(@Queries() WorkStudentParams params);
//
@GET("/api/hms/Annotate/Get")
Future<List<AnnotatedClass>> getAnnotatedClassList(@Query('homeworkId') String homeworkId);
//
@GET("/api/hms/HmsReport/GetHomeworkDtls")
Future<HomeworkDetails> getHomeworkDetails(@Query('homeworkId') String homeworkId,@Query('classId') String classId);
//
@GET("/api/hms/HmsReport/GetStudentHistory")
Future<StudentHistory> getStudentHistory(@Queries() StudentHistoryParams params);
//
@POST("/api/rbac/Student/PriorityAnnotateStudent")
Future getAnnotateStudent(@Field() String classId, @Field() int studentId,@Field() bool priorityAnnotate,@Field() int subject);
//
@GET("/api/hms/HmsReport/GetStudentHomework")
Future<StudentPersonalInfo> getStudentHomework(@Query('HomeworkId') String homeworkId,@Query('StudentId') int studentId);
//
@GET("/api/hms/HmsReport/GetKnowledgeReport")
Future<List<KnowledgePointsGrasp>> getKnowledgeReport(@Query('DateStart') String dateStart,@Query('DateEnd') String dateEnd,@Query('KnowledgeName') String knowledgeName);
//
@GET("/api/hms/HmsReport/GetKnowledgeReportDetail")
Future<List<KnowledgeReportDetail>> getKnowledgeReportDetail(@Query('DateStart') String dateStart,@Query('DateEnd') String dateEnd,@Query('KnowledgeId') int knowledgeId);
//
@GET("/api/hms/HmsReport/GetQuestionStudentState")
Future<List<Students>> getQuestionStudentState(@Query('HomeworkId') String homeworkId,@Query('TemplateId') int templateId,@Query('QuestionNo') int questionNo);
//
@POST("/api/hms/Homework/Collect")
Future getCollect(@Field() String homeworkId);
}

View File

@ -1,6 +0,0 @@
import 'package:school_asignment_app/common/request/rest_dio.dart';
import 'package:school_asignment_app/common/api/retrofit_client.dart';
mixin RequestToolMixin {
RetrofitClient getClient() => RequestTool.instance.getClient();
}

View File

@ -1,205 +0,0 @@
import 'package:flutter/material.dart';
import 'package:flutter_screenutil/flutter_screenutil.dart';
import 'package:get/get.dart';
import 'package:school_asignment_app/common/job/homework_details.dart';
import 'package:school_asignment_app/page/home_page/children/quick_data_check/quick_data_check_state.dart';
class Utils{
Utils._internal();
///
static void hideKeyboard() {
FocusScopeNode? currentFocus = Get.focusScope?.nearestScope;
if (currentFocus == null) {
return;
}
if (!currentFocus.hasPrimaryFocus && currentFocus.focusedChild != null) {
FocusManager.instance.primaryFocus?.unfocus();
}
}
//
static bool isPad([double mobilePhoneScale = 1.2]) {
return ScreenUtil().scaleWidth > mobilePhoneScale;
}
static String getDoubleRemoveZero(double? val, [String? defaultVal]) {
try {
if (val == null) throw Exception('数据为空');
List<String> _valArr = val.toString().split('.');
if (_valArr.length >= 2) {
if (int.parse(_valArr[1]) == 0) {
return val.toInt().toString();
}
return val.toString();
}
return val.toInt().toString();
} catch (e) {
return defaultVal ?? '';
}
}
///
static String doubleToStringAsFixed(double val, {int fractionDigits = 2}) {
return val.toStringAsFixed(fractionDigits).replaceAll(RegExp(r'\.0*$'), '');
}
static calcRate (int divisor, int dividend) {
if(dividend != 0){
return ((100 * divisor) / dividend);
// return ((100 * divisor) / dividend).toStringAsFixed(0);
}else{
return 0.0;
}
}
///
static String second2HMS(int sec, {bool isEasy = false}) {
String hms = "0";
if (!isEasy) hms = "0秒";
if (sec > 0) {
int h = sec ~/ 3600;
int m = (sec % 3600) ~/ 60;
int s = sec % 60;
if(h>0){
hms = "$h时$m分$s秒";
}else{
if(m>0){
hms = "$m分$s秒";
}else{
hms = "$s秒";
}
}
}
return hms;
}
static getHomeworkData(HomeworkDetails data){
CountData dataCount = CountData();
List<Dtls> kgt = data.dtls.where((w) => w.questionType == 1).toList();
dataCount.kgtAnswerCount = kgt.where((w) => w.state != 0).length;
dataCount.kgtOkCount = kgt.where((w) => w.state == 3).length;
dataCount.kgtDtlCount = kgt.length;
dataCount.kgtAnswerRate = Utils.calcRate(dataCount.kgtAnswerCount!, dataCount.kgtDtlCount!);
dataCount.kgtOkRate = Utils.calcRate(dataCount.kgtOkCount!, dataCount.kgtDtlCount!);
dataCount.kgtCount = data.questions.where((w) => w.questionType == 1).length;
List<Dtls> zgt = data.dtls.where((w) => w.questionType == 2).toList();
dataCount.zgtAnswerCount = zgt.where((w) => w.state != 0).length;
dataCount.zgtOkCount = zgt.where((w) => w.state == 3).length;
dataCount.zgtDtlCount = zgt.length;
dataCount.zgtAnswerRate = Utils.calcRate(dataCount.zgtAnswerCount!, dataCount.zgtDtlCount!);
dataCount.zgtOkRate = Utils.calcRate(dataCount.zgtOkCount!, dataCount.zgtDtlCount!);
dataCount.zgtCount = data.questions.where((w) => w.questionType == 2).length;
dataCount.studentCount = data.students.length;
dataCount.priorityStudents = data.students.where((w) => w.priorityAnnotate!).toList();
for(var que in data.questions){
List<Dtls> ques = data.dtls.where((w) => w.templateId == que.templateId && w.questionNo == que.questionNo).toList();
que.answerCount = ques.where((w) => w.state != 0).length;
que.answerRate = Utils.calcRate(que.answerCount!, dataCount.studentCount!);
int okCount = ques.where((w) => w.state == 3).length;
que.okRate = Utils.calcRate(okCount, dataCount.studentCount!) ;
que.priorityInfo = ques.where((w) {
return dataCount.priorityStudents!.indexWhere((s) {
w.studentName = s.studentName;
return s.studentId == w.studentId;
}) > -1 && w.state != 3;
}).toList();
que.answerNgStudents = ques.where((w) {
w.studentName = data.students.firstWhere((s) => s.studentId == w.studentId).studentName;
return w.state == 2;
}).toList();
que.noAnswerStudents = ques.where((w) {
return w.state == 0;
}).toList();
que.answerOkStudents = ques.where((w) {
return w.state == 3;
}).toList();
}
dataCount.studentSubmitCount = data.students.where((s) => s.state != 0).length;
for(var stu in data.students){
stu.kgtStu = kgt.where((w) => w.studentId == stu.studentId).toList();
stu.kgtStu!.sort((a, b) => a.questionNo.compareTo(b.questionNo));
stu.kgtOkCount = stu.kgtStu!.where((w) => w.state == 3).length;
stu.kgtErrorCount = stu.kgtStu!.where((w) => w.state == 2).length;
stu.kgtAnswerCount = stu.kgtStu!.where((w) => w.state != 0).length;
stu.zgtStu = zgt.where((w) => w.studentId == stu.studentId).toList();
stu.zgtStu!.sort((a, b) => a.questionNo.compareTo(b.questionNo));
stu.zgtOkCount = stu.zgtStu!.where((w) => w.state == 3).length;
stu.zgtErrorCount = stu.zgtStu!.where((w) => w.state == 2).length;
stu.zgtUnrated = stu.zgtStu!.where((w) => w.state == 1).length;
stu.zgtAnswerCount = stu.zgtStu!.where((w) => w.state != 0).length;
stu.allOk = data.dtls.where((w) {
if(stu.studentId == w.studentId){
stu.useTime = w.useTime;
}
for(var que in data.questions){
if(w.templateId == que.templateId && w.questionNo == que.questionNo){
w.answer = que.answer;
w.questionPicture = que.questionPicture;
}
}
return w.studentId == stu.studentId && w.state != 3;
} ).length??0;
if( (stu.kgtStu!.length - stu.kgtAnswerCount!) + (stu.zgtStu!.length-stu.zgtAnswerCount!) == (stu.kgtStu!.length + stu.zgtStu!.length)){
stu.allNotDone = true;
}else{
stu.allNotDone = false;
}
stu.noAnswerCount = data.dtls.where((w) => w.state == 0 && stu.studentId == w.studentId).length;
List<Questions> ques = data.questions;
stu.queDtls =data.dtls.where((w) => w.studentId == stu.studentId && ques.indexWhere((q) => w.templateId == q.templateId && w.questionNo == q.questionNo) > -1).toList();
int okCount = stu.queDtls!.where((w) => w.state == 3).length;
int ttlCount = stu.queDtls!.length;
stu.okRate = Utils.calcRate(okCount, ttlCount);
}
data.students.sort((a, b) {
int num1 = a.state;
int num2 = b.state;
return num2.compareTo(num1);
});
for(var know in data.knows){
List<Questions> ques = data.questions.where((w) => w.knows.indexWhere((k) => k.knowledgeId == know.knowledgeId) > -1).toList();
List<Dtls> queDtls = data.dtls.where((w) => ques.indexWhere((q) => w.templateId == q.templateId && w.questionNo == q.questionNo) > -1).toList();
know.okCount = queDtls.where((w) => w.state == 3).length;
know.ttlCount = queDtls.length;
know.okRate = Utils.calcRate(know.okCount!, know.ttlCount!);
}
return dataCount;
}
static DateTime getWeekStartDate() {
DateTime now = DateTime.now();
int dayOfWeek = now.weekday; // 17
int diff = dayOfWeek - 1; //
if (diff < 0) {
diff += 7; //
}
return now.subtract(Duration(days: diff)); //
}
static DateTime getWeekEndDate() {
DateTime now = DateTime.now();
int dayOfWeek = now.weekday; //
int diff = 7 - dayOfWeek; //
if (diff == 0) {
diff = 7; //
}
return now.add(Duration(days: diff)); //
}
}

View File

@ -1,93 +0,0 @@
import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
import 'package:flutter_localizations/flutter_localizations.dart';
import 'package:flutter_screenutil/flutter_screenutil.dart';
import 'package:get/get.dart';
import 'package:school_asignment_app/common/config/app_config.dart';
import 'package:school_asignment_app/common/config/colorUtils.dart';
import 'package:school_asignment_app/common/store/user_store.dart';
import 'package:school_asignment_app/common/utils/storage.dart';
import 'package:school_asignment_app/common/utils/utils.dart';
import 'package:school_asignment_app/routes/app_pages.dart';
import 'package:flutter_easyloading/flutter_easyloading.dart';
void main() async {
// Get
Get.testMode = true;
///
await Get.putAsync(() => StorageService().init());
/// UserStore
Get.put<UserStore>(UserStore().init());
SystemChrome.setEnabledSystemUIMode(SystemUiMode.manual, overlays: [SystemUiOverlay.top, SystemUiOverlay.bottom]); //
SystemChrome.setPreferredOrientations([DeviceOrientation.portraitUp]); //
runApp(const MyApp());
}
class MyApp extends StatelessWidget {
const MyApp({super.key});
// This widget is the root of your application.
@override
Widget build(BuildContext context) {
return ScreenUtilInit(
designSize: const Size(AppConfig.UI_WIDTH, AppConfig.UI_HEIGHT),
minTextAdapt: true,
splitScreenMode: true,
builder: (BuildContext context, Widget? child) => GetMaterialApp(
title: '作业',
theme: ThemeData(
brightness: Brightness.light,
primarySwatch: createMaterialColor(const Color.fromRGBO(46, 91, 255, 1)),
primaryColor: const Color.fromRGBO(46, 91, 255, 1),
// textTheme: Typography.englishLike2018.apply(fontSizeFactor: 1.sp,),
primaryTextTheme: TextTheme(
bodyLarge: TextStyle(fontSize: 14.sp, color: Colors.black87),
),
useMaterial3: true,
),
enableLog: true,
logWriterCallback: (text, {bool isError = false}) {
// isError ? LoggerUtils.e(text) : LoggerUtils.i(text);
},
// flutter_localizations依赖
supportedLocales: const [
Locale('zh', 'CN'), //
// locale可以在这里添加
],
localizationsDelegates: const [
// ...delegates
GlobalMaterialLocalizations.delegate,
GlobalWidgetsLocalizations.delegate,
GlobalCupertinoLocalizations.delegate, // 使Cupertino风格的组件
// ...delegates
],
localeResolutionCallback: (locale, supportedLocales) {
// locale解析逻辑
// Locale对象
return locale;
},
//
defaultTransition: Transition.fade,
//
initialRoute: Routes.startPage,
///
getPages: AppPages.pages,
builder: EasyLoading.init(
builder: (context, child) {
return MediaQuery(
//Setting font does not change with system font size
data: MediaQuery.of(context).copyWith(textScaleFactor: 1.0),
child: Scaffold(
body: GestureDetector(onTap: () => Utils.hideKeyboard(), child: child),
),
);
},
),
// home: const MyHomePage(title: 'Flutter Demo Home Page'),
),
);
}
}

View File

@ -1,121 +0,0 @@
import 'package:flutter/material.dart';
import 'package:flutter_screenutil/flutter_screenutil.dart';
import 'package:get/get.dart';
import 'package:package_info/package_info.dart';
import 'package:school_asignment_app/page/global_widget/my_text.dart';
//
class OhterPage extends StatefulWidget {
const OhterPage({super.key});
@override
State<OhterPage> createState() => _OhterPageState();
}
class _OhterPageState extends State<OhterPage> {
RxString localVersion = ''.obs;
@override
void initState() {
super.initState();
getPageInfo();
}
//
getPageInfo() async {
PackageInfo packageInfo = await PackageInfo.fromPlatform();
localVersion.value = packageInfo.version;
}
@override
Widget build(BuildContext context) {
final personalInfoTitleStly = TextStyle(
color: const Color.fromRGBO(80, 87, 103, 1),
fontSize: 16.sp,
);
final personalInfoValStly = TextStyle(
color: const Color.fromRGBO(148, 163, 182, 1),
fontSize: 16.sp,
);
return Scaffold(
backgroundColor: const Color.fromRGBO(248, 248, 248, 1),
appBar: AppBar(
backgroundColor: Theme.of(context).primaryColor,
title: quickText('其他', color: Colors.white),
),
body: Stack(
alignment: const FractionalOffset(0.5, 0.98),
children: [
ListView(
children: [
Container(
margin: EdgeInsets.symmetric(vertical: 22.h, horizontal: 16.w),
padding: EdgeInsets.symmetric(vertical: 22.h, horizontal: 16.w),
height: 130.h,
decoration: BoxDecoration(
borderRadius: BorderRadius.all(Radius.circular(6.w)),
color: Colors.white,
boxShadow: const [
BoxShadow(
color: Color.fromRGBO(46, 91, 255, 0.1),
offset: Offset.zero, //y轴偏移量
blurRadius: 20, //
spreadRadius: 10, //
)
],
),
child: Column(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
InkWell(
onTap: () {
/* RouterManager.router.navigateTo(
context,
transition: TransitionType.fadeIn,
'${RouterManager.agreementPath}?type=${AGREEMENT_KEY.PRIVACY_GREEMENT.name}',
);*/
},
child: Container(
padding: EdgeInsets.only(bottom: 4.h),
child: Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
Text('用户隐私协议', style: personalInfoTitleStly),
Icon(
Icons.arrow_forward_ios,
color: const Color.fromRGBO(80, 87, 103, 1),
size: 16.sp,
)
],
),
),
),
Container(
height: 1.w,
color: const Color.fromRGBO(240, 243, 255, 1),
),
SizedBox(height: 8.h),
Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
Text('APP版本', style: personalInfoTitleStly),
Obx(() {
return quickText(localVersion);
})
],
)
],
),
),
],
),
Row(
mainAxisSize: MainAxisSize.min,
mainAxisAlignment: MainAxisAlignment.center,
children: [Text('APP备案号: ', style: personalInfoTitleStly), quickText('渝ICP备17007225号-3A', size: 14.sp)],
),
],
));
}
}

View File

@ -1,55 +0,0 @@
import 'package:flutter_easyloading/flutter_easyloading.dart';
import 'package:get/get.dart';
import 'package:get_storage/get_storage.dart';
import 'package:school_asignment_app/common/job/annotated_class.dart';
import 'package:school_asignment_app/common/mixins/request_tool_mixin.dart';
import 'package:school_asignment_app/routes/app_pages.dart';
import 'annotate_class_state.dart';
class AnnotateClassLogic extends GetxController with RequestToolMixin{
final AnnotateClassState state = AnnotateClassState();
@override
void onInit(){
super.onInit();
state.homeworkId.value = Get.arguments['id']??'';
state.name.value = Get.arguments['name']??'';
state.grade = Get.arguments['grade'];
state.completed.value = Get.arguments['completed']??false;
EasyLoading.show(status: 'loading...');
getList();
}
void getList() async{
List<AnnotatedClass> data = await getClient(). getAnnotatedClassList(state.homeworkId.value);
state.classList.value = data;
for (var element in state.classList.value) {
int commitStudentCount = 0;
int noCommitStudentCount = 0;
for (var student in element.students) {
if(student.state == 0){
noCommitStudentCount ++;
}else{
commitStudentCount ++;
}
}
element.commitStudentCount = commitStudentCount;
element.noCommitStudentCount = noCommitStudentCount;
}
EasyLoading.dismiss();
}
void goQuickDataCheck(item){
Get.toNamed(Routes.quickDataCheckPage,arguments: {'homeworkId':state.homeworkId.value,'classId':item.classId,'grade':state.grade,'className':item.className
});
}
void gojobReport(item){
Get.toNamed(Routes.jobReportPage,arguments: {'title':state.name.value,'homeworkId':state.homeworkId.value,'grade':state.grade,'className':item.className});
}
}

View File

@ -1,95 +0,0 @@
import 'package:flutter/material.dart';
import 'package:flutter_screenutil/flutter_screenutil.dart';
import 'package:flutter_staggered_grid_view/flutter_staggered_grid_view.dart';
import 'package:get/get.dart';
import 'package:percent_indicator/percent_indicator.dart';
import 'package:school_asignment_app/common/job/annotated_class.dart';
import 'package:school_asignment_app/common/utils/utils.dart';
import 'package:school_asignment_app/page/global_widget/ReturnToHomepage.dart';
import 'package:school_asignment_app/page/global_widget/my_text.dart';
import 'package:school_asignment_app/page/home_page/children/annotate_class/widget/annotate_item.dart';
import 'package:school_asignment_app/page/home_page/widget/progress_bar.dart';
import 'package:school_asignment_app/routes/app_pages.dart';
import 'annotate_class_logic.dart';
import 'widget/completed_annotate_item.dart';
class AnnotateClassPage extends StatefulWidget {
const AnnotateClassPage({Key? key}) : super(key: key);
@override
State<AnnotateClassPage> createState() => _AnnotateClassPageState();
}
class _AnnotateClassPageState extends State<AnnotateClassPage> {
final logic = Get.find<AnnotateClassLogic>();
final state = Get.find<AnnotateClassLogic>().state;
@override
Widget build(BuildContext context) {
return Scaffold(
backgroundColor: const Color.fromRGBO(245, 245, 245, 1),
appBar: AppBar(
backgroundColor: Colors.white,
title: Obx(() {
return Text(state.name.value,
style:
TextStyle(fontSize: 14.sp, color: const Color(0xFF333333)));
}),
centerTitle: true,
leading: IconButton(
icon: const Icon(Icons.arrow_back_ios, color: Colors.black),
onPressed: () => Navigator.of(context).pop(),
),
actions: const [
ReturnToHomepage(),
],
),
body: Padding(
padding: EdgeInsets.symmetric(vertical: 14.r, horizontal: 14.r),
child: Obx(() {
return
state.completed.value? Utils.isPad()?GridView(
gridDelegate: SliverGridDelegateWithFixedCrossAxisCount(
crossAxisCount: 2, //widget
mainAxisSpacing: 10.h,
crossAxisSpacing: 6.w,
childAspectRatio: 1.48 //1widget
),
children: state.classList.map((taskItem) {
return CompletedAnnotateItem(taskItem:taskItem,logic: logic,);
}).toList(),
):ListView.builder(
itemCount: state.classList.length,
itemBuilder: (context, index) {
AnnotatedClass taskItem = state.classList[index];
return CompletedAnnotateItem(taskItem:taskItem,logic: logic,);
}):
Utils.isPad()?MasonryGridView.count(
crossAxisCount: 2, //
mainAxisSpacing: 4.w, //
crossAxisSpacing: 4.h, //
itemCount: state.classList.length,
itemBuilder: (context, index) {
AnnotatedClass item = state.classList[index];
return AnnotateItem(item: item,font: 8.sp,name: state.name.value,logic: logic,);
},
):
ListView.builder(
itemCount: state.classList.length,
itemBuilder: (context, index) {
AnnotatedClass item = state.classList[index];
return AnnotateItem(item: item,font: 12.sp,name: state.name.value,logic: logic,);
});
}),
),
);
}
@override
void dispose() {
Get.delete<AnnotateClassLogic>();
super.dispose();
}
}

View File

@ -1,241 +0,0 @@
import 'package:flutter/material.dart';
import 'package:flutter_screenutil/flutter_screenutil.dart';
import 'package:get/get.dart';
import 'package:percent_indicator/percent_indicator.dart';
import 'package:school_asignment_app/common/job/annotated_class.dart';
import 'package:school_asignment_app/common/utils/enum_untils.dart';
import 'package:school_asignment_app/page/global_widget/my_text.dart';
import 'package:school_asignment_app/page/home_page/children/annotate_class/annotate_class_logic.dart';
import 'package:school_asignment_app/page/home_page/children/annotate_class/annotate_class_state.dart';
import 'package:school_asignment_app/page/home_page/children/annotate_class/widget/item_btn.dart';
import 'package:school_asignment_app/page/home_page/widget/progress_bar.dart';
import 'package:school_asignment_app/routes/app_pages.dart';
class AnnotateItem extends StatefulWidget {
final AnnotatedClass item;
final double font;
final String name;
final AnnotateClassLogic logic;
const AnnotateItem({Key? key, required this.item,required this.font,required this.name,required this.logic}) : super(key: key);
@override
State<AnnotateItem> createState() => _AnnotateItemState();
}
class _AnnotateItemState extends State<AnnotateItem> {
@override
Widget build(BuildContext context) {
return Container(
padding: EdgeInsets.only(top: 10.r),
margin: EdgeInsets.only(bottom: 10.r),
decoration: BoxDecoration(
color: Colors.white,
borderRadius: BorderRadiusDirectional.circular(4.r),
boxShadow: const [BoxShadow(color: Color.fromRGBO(0, 0, 0, 0.15), blurRadius: 10)],
),
child: Column(
children: [
Padding(
padding: EdgeInsets.symmetric(horizontal: 10.r),
child: Row(
children: [
Text(
'${EnumUtils.formatGrade(widget.item.grade)}${widget.item.className}',
style: TextStyle(
fontSize: widget.font,
color: const Color(0xFF000000)),
),
const Spacer(),
Text(
'已交:${widget.item.commitStudentCount}',
style: TextStyle(
fontSize: widget.font - 2.sp,
color: const Color(0xFF6888FD)),
),
SizedBox(
width: 20.r,
),
Text(
'未交:${widget.item.noCommitStudentCount}',
style: TextStyle(
fontSize: widget.font - 2.sp,
color: const Color(0xFFFF5656)),
),
],
),
),
SizedBox(
height: 10.r,
),
Padding(
padding: EdgeInsets.symmetric(horizontal: 8.r),
child: Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children:
widget.item.finishTime != null ?
[
Expanded(
flex:4,
child:ItemBtn(title: "收藏夹",font: widget.font - 2.sp,
clickFunction: (){
},),
),
const Expanded(flex: 1, child: SizedBox()),
const Expanded(flex: 4, child: SizedBox()),
const Expanded(flex: 1, child: SizedBox()),
const Expanded(flex: 4, child: SizedBox()),
]:[
Expanded(
flex: 4,
child: ItemBtn(title: "一键批阅",font: widget.font - 2.sp,
clickFunction: (){
},),
),
const Expanded(flex: 1,child: Text(''),),
Expanded(
flex:4,
child: ItemBtn(title: "数据快查",font: widget.font - 2.sp,clickFunction: (){
widget.logic.goQuickDataCheck(widget.item);
},),
),
const Expanded(flex: 1,child: Text(''),),
Expanded(
flex:4,
child: ItemBtn(title: "收藏夹",font: widget.font - 2.sp,
clickFunction: (){
},),
),
],
),
),
Padding(
padding: EdgeInsets.symmetric(vertical: 10.r,horizontal: 14.r),
child: Row(
children: [
Expanded(
child: LinearPercentIndicator(
padding: EdgeInsets.zero,
animation: true,
lineHeight: 8.h,
animationDuration: 2500,
percent: widget.item.annotateRate / 100,
linearGradient: LinearGradient(
tileMode: TileMode.mirror,
stops: const [0.0, 1.0],
colors: widget.item.annotateRate / 100 != 1
? [Theme.of(context).primaryColor.withOpacity(0.1), Theme.of(context).primaryColor]
: [
const Color.fromRGBO(144, 224, 190, 1).withOpacity(0.1),
const Color.fromRGBO(144, 224, 190, 1),
],
),
// linearStrokeCap: LinearStrokeCap.butt,
// progressColor: Theme.of(context).primaryColor,
backgroundColor: const Color.fromRGBO(232, 232, 232, 1),
barRadius: Radius.circular(10.r),
),
),
SizedBox(width: 7.w),
quickText('${widget.item.annotateRate}%',
size: widget.font - 2.sp, color: const Color.fromRGBO(70, 70, 70, 1))
],
),
),
ProgressBar(
title: '客观题正确率:',
color: const Color(0xFFB8C7FF),
percent: widget.item.kgtCorrectRate / 100,
marginEdg: EdgeInsets.zero,
padingEdg: EdgeInsets.only(top: 8.h,left: 14.r,right: 14.r),
fontSize:widget.font - 2.sp),
ProgressBar(
title: '主观题正确率:',
color: const Color(0xFFB8C7FF),
percent: widget.item.zgtCorrectRate / 100,
padingEdg: EdgeInsets.symmetric(horizontal: 10.r),
marginEdg: EdgeInsets.only(top: 8.h),
fontSize:widget.font - 2.sp),
ProgressBar(
title: '总正确率:',
color: const Color(0xFFB8C7FF),
percent: widget.item.correctRate / 100,
padingEdg: EdgeInsets.symmetric(horizontal: 10.r),
marginEdg: EdgeInsets.only(top: 8.h),
fontSize:widget.font - 2.sp),
Container(
margin: EdgeInsets.only(top: 10.r),
decoration: BoxDecoration(
borderRadius: BorderRadius.only(bottomLeft: Radius.circular(4.r), bottomRight: Radius.circular(4.r)),
color: Colors.white,
boxShadow: const [
BoxShadow(
color: Color.fromRGBO(0, 0, 0, 0.15),
offset: Offset(0, -0.0001), //y轴偏移量
blurRadius: 4, //
spreadRadius: 0, //
)
],
),
child: Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children:
widget.item.finishTime != null ?
[
Expanded(
child: InkWell(
onTap: () {
widget.logic.goQuickDataCheck(widget.item);
},
child: Container(
alignment: Alignment.center,
child: quickText('数据快查', color: Color.fromRGBO(118, 118, 118, 1), size: widget.font),
),
),
),
Container(width: 1.w, height: 30.h, color: const Color.fromRGBO(221, 221, 221, 1)),
Expanded(
child: InkWell(
onTap: () {
widget.logic.gojobReport(widget.item);
},
child: Container(
alignment: Alignment.center,
child: quickText('查看报告', color: Color.fromRGBO(118, 118, 118, 1), size: widget.font),
),
)),
]
:
[
Expanded(
child: InkWell(
onTap: () {},
child: Container(
alignment: Alignment.center,
child: quickText('批阅', color: const Color.fromRGBO(118, 118, 118, 1), size: widget.font),
),
),
),
Container(width: 1.w, height: 30.h, color: const Color.fromRGBO(221, 221, 221, 1)),
Expanded(
child: InkWell(
onTap: () {},
child: Container(
alignment: Alignment.center,
child: quickText('结束批阅', color: const Color.fromRGBO(118, 118, 118, 1), size: widget.font),
),
)),
],
),
)
],
),
);
}
}

View File

@ -1,353 +0,0 @@
import 'package:flutter/material.dart';
import 'package:flutter_easyloading/flutter_easyloading.dart';
import 'package:flutter_easyrefresh/easy_refresh.dart';
import 'package:flutter_screenutil/flutter_screenutil.dart';
import 'package:get/get.dart';
import 'package:school_asignment_app/common/job/student_item.dart';
import 'package:school_asignment_app/common/utils/utils.dart';
import 'package:school_asignment_app/page/global_widget/MyEmptyWidget.dart';
import 'package:school_asignment_app/page/global_widget/ReturnToHomepage.dart';
import 'package:school_asignment_app/routes/app_pages.dart';
import 'class_student_logic.dart';
class ClassStudentPage extends StatefulWidget {
const ClassStudentPage({Key? key}) : super(key: key);
@override
State<ClassStudentPage> createState() => _ClassStudentPageState();
}
class _ClassStudentPageState extends State<ClassStudentPage> {
final logic = Get.find<ClassStudentLogic>();
final state = Get
.find<ClassStudentLogic>()
.state;
@override
Widget build(BuildContext context) {
return Scaffold(
backgroundColor: const Color.fromRGBO(245, 245, 245, 1),
appBar: AppBar(
backgroundColor: Colors.white,
title: Obx(() {
return Text(
state.title.value,
style: TextStyle(fontSize: 14.sp, color: const Color(0xFF333333)),
);
}),
centerTitle: true,
leading: IconButton(
icon: const Icon(Icons.arrow_back_ios, color: Colors.black),
onPressed: () => Navigator.of(context).pop(),
),
actions: const [
ReturnToHomepage(),
],
),
body: Padding(
padding: EdgeInsets.symmetric(vertical: 14.r, horizontal: 14.r),
child: Obx(() {
return EasyRefresh(
firstRefresh: false,
taskIndependence: true,
controller: logic.refreshController,
header: MaterialHeader(),
footer: TaurusFooter(),
onRefresh: () async {
logic.getList();
},
child: state.studentList.isNotEmpty
? Utils.isPad()
? GridView(
shrinkWrap: true,
gridDelegate:
SliverGridDelegateWithFixedCrossAxisCount(
crossAxisCount: 2,
mainAxisSpacing: 10.r,
crossAxisSpacing: 10.r,
childAspectRatio: 556 / 112,
),
children: List.generate(state.studentList.length, (index) {
StudentItem item = state.studentList[index];
return InkWell(
onTap: () {
// RouterManager.router.navigateTo(context,
// '${RouterManager.jobPersonalDetailPath}?studentId=${item.studentId}&studentName=${Uri.encodeComponent(item.studentName)}');
Get.toNamed(Routes.studentWorkDetailPage,arguments: {'studentName':item.name,'studentId':item.id});
},
child: Container(
padding: EdgeInsets.symmetric(horizontal: 10.r),
decoration: BoxDecoration(
borderRadius:
BorderRadius.all(Radius.circular(10.r)),
color: Colors.white,
),
child: Row(
mainAxisAlignment:
MainAxisAlignment.spaceBetween,
children: [
Expanded(
child: Text(
item.name,
style: TextStyle(
fontSize: 12.sp,
color: const Color(0xFF6888FD)),
)),
state.page == 'answerTrajectory' ? Container(
height: 20.r,
width: 70.r,
decoration: BoxDecoration(
border: Border.all(
width: 1.r, color: const Color(0xFFFFA41E)),
borderRadius: BorderRadius.all(
Radius.circular(20.r)),
),
child: Center(child: Text('详情', style: TextStyle(
fontSize: 10.r, color: Color(0xFFFFA41E))),
)) : state.page == 'history' ? Container(
height: 20.r,
width: 70.r,
decoration: BoxDecoration(
color: const Color(0xFF6888FD),
borderRadius: BorderRadius.all(
Radius.circular(20.r))
),
child: Center(child: Text('历史作业', style: TextStyle(
fontSize: 10.r, color: Colors.white),)),
) :
item.priorityAnnotate
?
InkWell(
onTap: () {
logic.setJobReadLevel(
item.id, false);
EasyLoading.show(
status: 'loading...');
},
child: Container(
height: 20.r,
width: 80.r,
decoration: BoxDecoration(
borderRadius: BorderRadius.all(
Radius.circular(4.r)),
color: const Color(0xFFB7FFE0),
),
child: Row(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Padding(
padding: EdgeInsets.only(left: 3.r),
child: Image.asset(
'assets/images/youx_icon_active.png',
width: 14.r, height: 14.r,),
),
Padding(
padding: EdgeInsets.only(
top: 2.r, left: 4.r),
child: Text(
'优先批阅',
style: TextStyle(
fontSize: 10.sp,
color: const Color(0xFF4CC793)),
),
),
],
),
),
)
: InkWell(
onTap: () {
logic.setJobReadLevel(
item.id, true);
EasyLoading.show(
status: 'loading...');
},
child: Container(
height: 20.r,
width: 80.r,
decoration: BoxDecoration(
borderRadius: BorderRadius.all(
Radius.circular(4.r)),
color: const Color(0xFFE1E1E1),
),
child: Row(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Padding(
padding: EdgeInsets.only(left: 3.r),
child: Image.asset(
'assets/images/youx_icon_default.png',
width: 14.r, height: 14.r,),
),
Padding(
padding: EdgeInsets.only(
top: 2.r, left: 4.r),
child: Text(
'优先批阅',
style: TextStyle(
fontSize: 10.sp,
color: const Color(0xFF8A9691)),
),
),
],
),
),
),
],
),
),
);
}),
)
: ListView.builder(
itemBuilder: (context, index) {
StudentItem item = state.studentList[index];
return InkWell(
onTap: () {
// RouterManager.router.navigateTo(context,
// '${RouterManager.jobPersonalDetailPath}?studentId=${item.studentId}&studentName=${Uri.encodeComponent(item.studentName)}');
Get.toNamed(Routes.studentWorkDetailPage,arguments: {'studentName':item.name,'studentId':item.id});
},
child: Container(
padding: EdgeInsets.symmetric(
vertical: 20.r, horizontal: 15.r),
margin: EdgeInsets.only(bottom: 15.r),
decoration: BoxDecoration(
borderRadius:
BorderRadius.all(Radius.circular(10.r)),
color: Colors.white,
),
child: Row(
mainAxisAlignment:
MainAxisAlignment.spaceBetween,
children: [
Expanded(
child: Text(
item.name,
style: TextStyle(
fontSize: 12.sp,
color: Color(0xFF6888FD)),
)),
state.page == 'answerTrajectory' ? Container(
height: 24.r,
width: 72.r,
decoration: BoxDecoration(
border: Border.all(
width: 1.r, color: Color(0xFFFFA41E)),
borderRadius: BorderRadius.all(
Radius.circular(20.r)),
),
child: Center(child: Text('详情', style: TextStyle(
fontSize: 10.r, color: Color(0xFFFFA41E))),
)) : state.page == 'history' ? Container(
height: 24.r,
width: 82.r,
decoration: BoxDecoration(
color: Color(0xFF6888FD),
borderRadius: BorderRadius.all(
Radius.circular(20.r))
),
child: Center(child: Text('历史作业', style: TextStyle(
fontSize: 10.r, color: Colors.white),)),
) :
item.priorityAnnotate
? InkWell(
onTap: () {
logic.setJobReadLevel(
item.id, false);
EasyLoading.show(
status: 'loading...');
},
child: Container(
height: 24.r,
width: 82.r,
decoration: BoxDecoration(
borderRadius: BorderRadius.all(
Radius.circular(4.r)),
color: Color(0xFFB7FFE0),
),
child: Row(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Padding(
padding: EdgeInsets.only(left: 3.r),
child: Image.asset(
'assets/images/youx_icon_active.png',
width: 14.r, height: 14.r,),
),
Padding(
padding: EdgeInsets.only(
top: 2.r, left: 4.r),
child: Text(
'优先批阅',
style: TextStyle(
fontSize: 10.sp,
color: const Color(0xFF4CC793)),
),
),
],
),
),
)
: InkWell(
onTap: () {
logic.setJobReadLevel(
item.id, true);
EasyLoading.show(
status: 'loading...');
},
child: Container(
height: 24.r,
width: 82.r,
decoration: BoxDecoration(
borderRadius: BorderRadius.all(
Radius.circular(4.r)),
color: const Color(0xFFE1E1E1),
),
child: Row(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Padding(
padding: EdgeInsets.only(left: 3.r),
child: Image.asset(
'assets/images/youx_icon_default.png',
width: 14.r, height: 14.r,),
),
Padding(
padding: EdgeInsets.only(
top: 2.r, left: 4.r),
child: Text(
'优先批阅',
style: TextStyle(
fontSize: 10.sp,
color: const Color(0xFF8A9691)),
),
),
],
),
),
),
],
),
),
);
},
itemCount: state.studentList.length,
)
: const MyEmptyWidget(),
);
}),
),
);
}
@override
void dispose() {
Get.delete<ClassStudentLogic>();
super.dispose();
}
}

View File

@ -1,54 +0,0 @@
import 'package:flutter_easyloading/flutter_easyloading.dart';
import 'package:get/get.dart';
import 'package:school_asignment_app/common/job/annotated_class.dart';
import 'package:school_asignment_app/common/job/homework_details.dart';
import 'package:school_asignment_app/common/mixins/request_tool_mixin.dart';
import 'package:school_asignment_app/common/utils/utils.dart';
import 'job_report_state.dart';
class JobReportLogic extends GetxController with RequestToolMixin {
final JobReportState state = JobReportState();
@override
void onInit(){
super.onInit();
state.title.value = Get.arguments['title']??'';
state.homeworkId.value = Get.arguments['homeworkId']??'';
state.classId.value = Get.arguments['classId']??'';
state.className.value = Get.arguments['className']??'';
state.grade = Get.arguments['grade']??'';
EasyLoading.show(status: 'loading...');
getClass();
}
void getClass() async{
List<AnnotatedClass> data = await getClient(). getAnnotatedClassList(state.homeworkId.value);
state.involveClasses.value = data;
state.involveClasses.value = [state.classData.value, ...(data ?? [])];
for (var element in state.involveClasses) {
if (element.className == state.className.value && element.grade == state.grade ) {
state.classData.value = element;
}
}
getWorkData();
}
void getWorkData() async{
HomeworkDetails data = await getClient(). getHomeworkDetails(state.homeworkId.value,state.classData.value.classId != '-1' ? state.classData.value.classId : '');
state.dataCount = Utils.getHomeworkData(data);
state.homeData = data;
state.kgReport.value = data.questions.where((w)=>w.questionType == 1).toList();
state.zgReport.value = data.questions.where((w)=>w.questionType == 2).toList();
state.studentList.value = [...data.students];
state.knowsList.value = data.knows;
state.hasData.value = true;
EasyLoading.dismiss();
state.studentList.sort((a, b) {
int num1 = a.kgtOkCount!+a.zgtOkCount!;
int num2 = b.kgtOkCount!+b.zgtOkCount!;
return num2.compareTo(num1);
});
}
}

View File

@ -1,131 +0,0 @@
import 'package:flutter/material.dart';
import 'package:flutter_screenutil/flutter_screenutil.dart';
import 'package:get/get.dart';
import 'package:school_asignment_app/common/job/annotated_class.dart';
import 'package:school_asignment_app/page/global_widget/MyEmptyWidget.dart';
import 'package:school_asignment_app/page/global_widget/ReturnToHomepage.dart';
import 'package:school_asignment_app/page/home_page/children/job_report/widget/dropdown_selection.dart';
import 'package:school_asignment_app/page/global_widget/my_text.dart';
import 'package:school_asignment_app/page/home_page/children/job_report/widget/knowledge_point.dart';
import 'package:school_asignment_app/page/home_page/children/job_report/widget/personnel_data_overview.dart';
import 'package:school_asignment_app/page/home_page/children/quick_data_check/widget/kgt_zgt_table.dart';
import 'job_report_logic.dart';
class JobReportPage extends StatefulWidget {
const JobReportPage({Key? key}) : super(key: key);
@override
State<JobReportPage> createState() => _JobReportPageState();
}
class _JobReportPageState extends State<JobReportPage> {
final logic = Get.find<JobReportLogic>();
final state = Get
.find<JobReportLogic>()
.state;
@override
Widget build(BuildContext context) {
return Scaffold(
backgroundColor: Color.fromRGBO(245, 245, 245, 1),
appBar: AppBar(
backgroundColor: Colors.white,
centerTitle: true,
title: Center(
child: Obx(() {
return quickText(
'${state.title.value}作业报告',
size: 14.sp,
color: const Color.fromRGBO(51, 51, 51, 1),
);
})),
leading: IconButton(
icon: const Icon(Icons.arrow_back_ios, color: Colors.black),
onPressed: () => Navigator.of(context).pop(),
),
actions: const [
ReturnToHomepage(),
],
),
body: Obx(() {
if (state.hasData.value) {
return SingleChildScrollView(
child: Column(
children: [
//
Container(
padding: EdgeInsets.symmetric(vertical: 10.h, horizontal: 10.w),
decoration: const BoxDecoration(
color: Colors.white,
),
child: Row(
children: [
Obx(() {
return DropdownSelection(involveClasses: state
.involveClasses.value,
classData: state.classData.value,
call: (AnnotatedClass item) {
state.classData.value = item;
if (item.grade == -1) state.classData.value = state.defaultClass;
logic.getWorkData();
});
}),
// Expanded(child: Text('')),
],
),
),
//
/* TopCount(
data, classData == null ? '' : classData!.className, widget.id),*/
//
KgtZgtTable(studentCount: state.dataCount.studentCount!,
homeworkId: state.homeworkId.value,
kgReport: state.kgReport,
zgReport: state.zgReport,
kgtOkRate: state.dataCount.kgtOkRate!
.toStringAsFixed(0),
zgtOkRate: state.dataCount.zgtOkRate!
.toStringAsFixed(0)),
//
Container(
margin: EdgeInsets.symmetric(horizontal: 10.r),
child: KnowledgePoint(
knowsList:state.knowsList,data:state.homeData,className: state.classData.value.className,homeworkId:state.homeworkId.value)),
//
/* Container(
margin: EdgeInsets.symmetric(horizontal: 10.r),
child: $OverallPerformance(data.studentCount, data.overallTitles)),
//
Container(
margin: EdgeInsets.symmetric(horizontal: 10.r),
child: $UnitTimeAnsweringSituation(widget.id, data.questionAnswerInfos)),*/
//
Container(
margin: EdgeInsets.symmetric(horizontal: 10.r),
child: PersonnelDataOverview(studentList:state.studentList.value)),
SizedBox(height: 30.r,),
],
),
);
} else {
return Padding(
padding: EdgeInsets.only(
top: MediaQuery
.of(context)
.size
.height / 2 - 200.r),
child: const MyEmptyWidget()
);
}
}),
);
}
@override
void dispose() {
Get.delete<JobReportLogic>();
super.dispose();
}
}

View File

@ -1,299 +0,0 @@
import 'package:flutter/material.dart';
import 'package:flutter_screenutil/flutter_screenutil.dart';
import 'package:get/get.dart';
import 'package:percent_indicator/linear_percent_indicator.dart';
import 'package:school_asignment_app/common/job/homework_details.dart';
import 'package:school_asignment_app/common/utils/utils.dart';
import 'package:school_asignment_app/page/global_widget/MyEmptyWidget.dart';
import 'package:school_asignment_app/page/global_widget/my_text.dart';
import 'package:school_asignment_app/routes/app_pages.dart';
class KnowledgePoint extends StatefulWidget {
final RxList<Knows> knowsList;
final HomeworkDetails data;
final String className;
final String homeworkId;
KnowledgePoint({Key? key,required this.knowsList,required this.data,required this.className,required this.homeworkId}) : super(key: key);
@override
State<KnowledgePoint> createState() => _KnowledgePointState();
}
class _KnowledgePointState extends State<KnowledgePoint> {
void goQuickCheckPersonalPath(studentId) {
if (studentId != null) {
Get.toNamed(Routes.studentPersonalPage,arguments: {'studentId':studentId,'homeworkId':widget.homeworkId});
}
}
void showPeopleListDialog(
{required BuildContext context,
required String title,
required List<Students> arr,}) {
showDialog(
context: context,
builder: (BuildContext context) {
return AlertDialog(
// insetPadding: EdgeInsets.symmetric(vertical: 20.r,horizontal: 20.r),
backgroundColor:const Color(0xFFFFFFFF),
contentPadding: EdgeInsets.all(20.r),
shape: RoundedRectangleBorder(
borderRadius: BorderRadius.all(Radius.circular(15.r))),
content: SizedBox(
width: MediaQuery.of(context).size.width * 0.7,
height: MediaQuery.of(context).size.height * 0.7,
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Center(
child: Text(
title,
style: TextStyle(
fontSize: 15.sp,
color: const Color(0xFF3C3C3C),
fontWeight: FontWeight.w500),
),
),
SizedBox(
height: 10.r,
),
Row(
children: [
Expanded(
flex: 2,
child: Center(
child: Text(
'姓名',
style: TextStyle(
fontSize: 12.sp,
color: const Color(0xFF6A6A6A)),
))),
SizedBox(width: 10.r,),
Expanded(
flex: 1,
child: Center(
child: Text(
'班级',
style: TextStyle(
fontSize: 12.sp,
color: const Color(0xFF6A6A6A)),
))),
SizedBox(width: 10.r,),
Expanded(
flex: 2,
child: Center(
child: Text(
'掌握度',
style: TextStyle(
fontSize: 12.sp,
color: const Color(0xFF6A6A6A)),
))),
SizedBox(width: 10.r,),
Expanded(
flex: 3,
child: Center(
child: Text(
'掌握情况',
style: TextStyle(
fontSize: 12.sp,
color: const Color(0xFF6A6A6A)),
))),
],
),
SizedBox(
height: 5.r,
),
arr.isNotEmpty? Expanded(
child: ListView.builder(
shrinkWrap: true,
itemBuilder: (context, index) {
var item = arr[index];
return Container(
padding: EdgeInsets.symmetric(vertical: 5.r),
color: const Color(0xFFF0F0F0),
margin:EdgeInsets.only(bottom: 2.r),
child: Row(
children: [
Expanded(
flex: 2,
child: InkWell(
onTap: () {
goQuickCheckPersonalPath(
item.studentId);
},
child: Center(
child: Text(
item.studentName!,
style: TextStyle(
fontSize: 12.sp,
color: const Color(0xFF323232)),
)))),
SizedBox(width: 10.r,),
Expanded(
flex: 1,
child: Center(
child: Text(
widget.className == ''?'全部': widget.className,
style: TextStyle(
fontSize: 12.sp,
color: Color(0xFF323232)),
))),
SizedBox(width: 10.r,),
Expanded(
flex: 2,
child: Center(
child: Text(
'${item.okRate!.toStringAsFixed(0)}%',
style: TextStyle(
fontSize: 12.sp,
color: Color(0xFF323232)),
))),
SizedBox(width: 10.r,),
Expanded(
flex: 3,
child: Padding(
padding: EdgeInsets.symmetric(vertical: 2.r, horizontal: 5.r),
child: SingleChildScrollView(
child: Wrap(
direction: Axis.horizontal,
alignment: WrapAlignment.start,
spacing: 5,
runSpacing: 3,
children: List.generate(item.queDtls!.length, (index) {
Dtls kgInfo = item.queDtls![index];
return Container(
width: 14.r,
height: 14.r,
decoration: BoxDecoration(
color: kgInfo.state == 0
? const Color(0xFFD3D3D3)
: kgInfo.state == 1?Colors.white:kgInfo.state == 2
? const Color(0xFFFF7474)
: const Color(0xFF4CC793),
borderRadius: BorderRadius.all(Radius.circular(7.r))),
child: Center(
child: Text(
kgInfo.questionNo.toString(),
style: TextStyle(
fontSize: 8.sp,
color: kgInfo.state == 1
? Color(0xFF525252)
: Colors.white),
)),
);
})),
),
),),
],
),
);
},
itemCount: arr.length,
),
): const MyEmptyWidget()
],
),
),
);
});
}
@override
Widget build(BuildContext context) {
return Container(
margin: EdgeInsets.only(top: 10.h),
padding: EdgeInsets.symmetric(vertical: 16.h, horizontal: 12.w),
constraints: BoxConstraints(maxHeight: 320.h),
decoration: BoxDecoration(color: Colors.white, borderRadius: BorderRadius.circular(10.r)),
child: Column(
children: [
Container(
margin: EdgeInsets.only(bottom: 24.h),
child: quickText('知识点掌握情况', color: const Color.fromRGBO(92, 92, 92, 1), size: 14.sp, fontWeight: FontWeight.bold),
),
Expanded(
child: ListView(children: widget.knowsList.value.map((item) {
return Container(
margin: EdgeInsets.only(bottom: 15.h, left: 15.r, right: 15.r),
child: Column(
mainAxisSize: MainAxisSize.min,
crossAxisAlignment: CrossAxisAlignment.start,
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
Row(
children: [
Expanded(
flex: 10,
child: Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
quickText(item.knowledgeName,
size: 12.sp, color: const Color.fromRGBO(152, 152, 152, 1)),
quickText('${item.okRate!.toStringAsFixed(0)}%',
size: 12.sp, color: const Color.fromRGBO(64, 64, 64, 1)),
],
),
),
SizedBox(width: 10.w),
const Expanded(flex: 1, child: SizedBox()),
],
),
SizedBox(height: 3.h),
Row(
mainAxisAlignment: MainAxisAlignment.spaceBetween,
children: [
Expanded(
flex: 10,
child: LinearPercentIndicator(
padding: EdgeInsets.zero,
animation: true,
lineHeight: 10.h,
animationDuration: 2500,
percent: item.okRate! / 100,
progressColor: Theme.of(context).primaryColor,
backgroundColor: const Color.fromRGBO(219, 224, 243, 1),
barRadius: Radius.circular(10.r),
)),
SizedBox(width: 10.w),
InkWell(
onTap: () {
List<Questions> ques = widget.data.questions.where((w) => w.knows.indexWhere((k) => k.knowledgeId == item.knowledgeId) > -1).toList();
List<Students> array2 = [...widget.data.students];
for(var stu in array2){
stu.queDtls = widget.data.dtls.where((w) => w.studentId == stu.studentId && ques.indexWhere((q) => w.templateId == q.templateId && w.questionNo == q.questionNo) > -1).toList();
int okCount = stu.queDtls!.where((w) => w.state == 3).length;
int ttlCount = stu.queDtls!.length;
stu.okRate = Utils.calcRate(okCount, ttlCount);
stu.queDtls!.sort((a, b) {
int num1 = a.questionNo;
int num2 = b.questionNo;
return num1.compareTo(num2);
});
}
showPeopleListDialog(
context: context,
title: item.knowledgeName,
arr: array2,);
},
child: Row(
mainAxisSize: MainAxisSize.min,
children: [
quickText('查看', size: 12.sp, color: const Color.fromRGBO(239, 135, 20, 1)),
Icon(Icons.arrow_forward_ios, size: 11.sp, color: const Color.fromRGBO(239, 135, 20, 1)),
],
),
),
],
)
],
),
);
}).toList()),
),
],
));
}
}

View File

@ -1,16 +0,0 @@
import 'package:get/get.dart';
import 'package:school_asignment_app/common/job/knowledge_points_grasp.dart';
import 'package:school_asignment_app/common/utils/utils.dart';
class KnowledgePointsGraspState {
KnowledgePointsGraspState() {
///Initialize variables
}
late int page = 1;
late int totalPages = 0;
late RxList<KnowledgePointsGrasp> dataList=RxList();
late String dateStart = Utils.getWeekStartDate().toString().substring(0, 10);
late String dateEnd = Utils.getWeekEndDate().toString().substring(0, 10);
late RxString customTimeStr = '自定义'.obs;
}

View File

@ -1,265 +0,0 @@
import 'package:flutter/material.dart';
import 'package:flutter_easyloading/flutter_easyloading.dart';
import 'package:flutter_easyrefresh/easy_refresh.dart';
import 'package:flutter_screenutil/flutter_screenutil.dart';
import 'package:get/get.dart';
import 'package:school_asignment_app/common/job/knowledge_points_grasp.dart';
import 'package:school_asignment_app/common/utils/utils.dart';
import 'package:school_asignment_app/page/global_widget/MyEmptyWidget.dart';
import 'package:school_asignment_app/page/global_widget/ReturnToHomepage.dart';
import 'package:school_asignment_app/page/home_page/children/student_work_detail/widget/job_condition_filter.dart';
import 'package:school_asignment_app/page/home_page/widget/progress_bar.dart';
import 'package:school_asignment_app/routes/app_pages.dart';
import 'package:syncfusion_flutter_datepicker/datepicker.dart';
import 'knowledge_points_grasp_logic.dart';
class KnowledgePointsGraspPage extends StatefulWidget {
const KnowledgePointsGraspPage({Key? key}) : super(key: key);
@override
State<KnowledgePointsGraspPage> createState() =>
_KnowledgePointsGraspPageState();
}
class _KnowledgePointsGraspPageState extends State<KnowledgePointsGraspPage> {
final logic = Get.find<KnowledgePointsGraspLogic>();
final state = Get
.find<KnowledgePointsGraspLogic>()
.state;
@override
Widget build(BuildContext context) {
return Scaffold(
backgroundColor: Color.fromRGBO(245, 245, 245, 1),
appBar: AppBar(
backgroundColor: Colors.white,
title: Text('知识点掌握',
style: TextStyle(fontSize: 14.sp, color: Color(0xFF333333))),
centerTitle: true,
leading: IconButton(
icon: Icon(Icons.arrow_back_ios, color: Colors.black),
onPressed: () => Navigator.of(context).pop(),
),
actions: const [
ReturnToHomepage(),
],
elevation: 0,
),
body: Column(
children: [
Container(
margin: EdgeInsets.all(15.r),
height: 30.r,
child: Row(
children: [
Expanded(
child: Container(
padding: EdgeInsets.only(left: 10.r, right: 10.r),
decoration: BoxDecoration(
borderRadius: BorderRadius.circular(6.r),
border: Border.all(width: 1.r, color: Color(0xFFDDDDDD)),
color: Colors.white,
),
child: TextField(
controller: logic.textController,
textInputAction: TextInputAction.next,
style: TextStyle(
color: const Color.fromRGBO(80, 87, 103, 1),
fontSize: 10.sp,
),
decoration: InputDecoration(
hintText: "请输入知识点名称",
hintStyle: TextStyle(fontSize: 10.sp,
color: const Color.fromRGBO(153, 153, 153, 1)),
labelStyle: TextStyle(fontSize: 10.sp,
color: const Color.fromRGBO(148, 163, 182, 1)),
border: InputBorder.none,
),
),
),
),
SizedBox(width: 10.r,),
InkWell(
onTap: () {
state.page = 1;
logic.getList();
},
child: Container(
width: 50.r,
height: 30.r,
decoration: BoxDecoration(
borderRadius: BorderRadius.circular(4.r),
color: Color(0xFF6888FD),
),
child: Center(
child: Text('查询', style: TextStyle(
fontSize: 12.sp, color: Colors.white),),
),
),
)
],
),
),
Obx(() {
return JobConditionFilter(
jobType: 1,
controller: logic.tabController,
customTimeStr: state.customTimeStr.value,
customTime: logic.tabController.index != 2 ||
((state.dateEnd == null || state.dateEnd == '') &&
(state.dateStart == null || state.dateStart == ''))
? null
: PickerDateRange(
state.dateStart == null || state.dateStart == ''
? null
: DateTime
.parse(state.dateStart!),
state.dateEnd == null || state.dateEnd == '' ? null : DateTime
.parse(state.dateEnd!),
),
onTimeFilter: (String? startTime, String? endTime) {
EasyLoading.show(status: 'loading...');
if (startTime == null && endTime == null) {
if (logic.tabController.index == 2) {
logic.tabController.animateTo(0);
}
state.dateStart = Utils.getWeekStartDate().toString().substring(0, 10);
state.dateEnd = Utils.getWeekEndDate().toString().substring(0, 10);
state.customTimeStr.value = '自定义';
} else {
state.dateStart = startTime ?? '';
state.dateEnd = endTime ?? '';
}
state.page = 1;
logic.getList();
// _refreshController2.callRefresh();
},
refreshTime: (value) {
if (value != null && value.startDate != null) {
state.customTimeStr.value =
value.startDate?.toString().substring(0, 10) ?? '';
if (value.endDate != null) {
if (!Utils.isPad() &&
value.startDate!.year == value.endDate!.year) {
state.customTimeStr.value =
'${value.startDate.toString().substring(5, 10)}~${value
.endDate.toString().substring(5, 10)}';
} else {
state.customTimeStr.value =
'${state.customTimeStr.value}~${value.endDate?.toString()
.substring(0, 10)}';
}
}
}
},);
}),
Expanded(
child: Padding(
padding: EdgeInsets.symmetric(vertical: 10.r),
child: Obx(() {
return EasyRefresh(
firstRefresh: false,
taskIndependence: true,
controller: logic.refreshController,
header: MaterialHeader(),
footer: TaurusFooter(),
onRefresh: () async {
state.page = 1;
logic.getList();
},
onLoad: () async {
if (state.page < state.totalPages) {
state.page += 1;
logic.getList();
}
},
child: state.dataList.isNotEmpty
? ListView.builder(
itemCount: state.dataList.value.length,
itemBuilder: (context, index) {
KnowledgePointsGrasp item = state.dataList[index];
return InkWell(
onTap: () {
Get.toNamed(Routes.knowledgePointsGraspDetailPage,arguments: {'dateStart':state.dateStart,'dateEnd':state.dateEnd,'knowledgeId':item.knowledgeId,'knowledgeName':item.knowledgeName});
},
child: Container(
margin: EdgeInsets.symmetric(
vertical: 5.r, horizontal: 14.r),
padding: EdgeInsets.symmetric(
vertical: 14.r, horizontal: 10.r),
decoration: BoxDecoration(
borderRadius: BorderRadius.all(
Radius.circular(10.r)),
color: Colors.white),
child: Column(
mainAxisAlignment: MainAxisAlignment.start,
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Row(
mainAxisAlignment: MainAxisAlignment.start,
crossAxisAlignment: CrossAxisAlignment.end,
children: [
Expanded(
child: Text(
item.knowledgeName,
style: TextStyle(fontSize: 14.sp,
color: Color(0xFF505050)),
)),
Container(
width: 49.r,
height: 22.r,
decoration: BoxDecoration(
borderRadius: BorderRadius.all(
Radius.circular(20.r)),
border: Border.all(width: 1.r,
color: Color(0xFF6888FD)),
),
child: Row(
mainAxisAlignment: MainAxisAlignment
.center,
children: [
Text(
'${item.count}',
style: TextStyle(fontSize: 10.sp,
color: Color(0xFF6888FD)),
),
Image.asset(
'assets/images/right_icon_blue.png',
width: 8.r, height: 8.r,),
],
),
),
],
),
SizedBox(height: 10.r,),
ProgressBar(
title: '正确率:',
color: Color(0xFF90E0BE),
percent: item.correctRate / 100,
padingEdg: EdgeInsets.zero,
marginEdg: EdgeInsets.only(top: 8.h)),
],
),
),
);
})
: const MyEmptyWidget(),
);
}),
),
),
],
),
);
}
@override
void dispose() {
Get.delete<KnowledgePointsGraspLogic>();
super.dispose();
}
}

Some files were not shown because too many files have changed in this diff Show More