I'm currently working on developing a quiz using Angular JS and Ionic Framework. However, I've encountered an issue:
The "Continue" button is not functioning as expected when clicked (using ng-click) to move to the next question.
<div class="btn" ng-click="selectContinue()">Continue</div>
Here is the function associated with the button:
$scope.selectContinue = function(){
return $scope.activeQuestion += 1;
}
https://i.sstatic.net/9W98N.png
<div class="feedback">
<p ng-show="myQuestion.correctness === 'correct'">You are <strong>correct</strong>.</p>
<p ng-show="myQuestion.correctness === 'incorrect'">Oops! That is not correct.</p>
<p>{{ myQuestion.feedback }}</p>
<div class="btn" ng-click="selectContinue()">Continue</div>
</div>
If you need to review the app.js, the selectContinue function is located below:
// Ionic Starter App
// angular.module is a global place for creating, registering and retrieving Angular modules
// 'starter' is the name of this angular module example (also set in a <body> attribute in index.html)
// the 2nd parameter is an array of 'requires'
angular.module('starter', ['ionic'])
.run(function($ionicPlatform) {
$ionicPlatform.ready(function() {
if(window.cordova && window.cordova.plugins.Keyboard) {
// Hide the accessory bar by default (remove this to show the accessory bar above the keyboard
// for form inputs)
cordova.plugins.Keyboard.hideKeyboardAccessoryBar(true);
// Don't remove this line unless you know what you are doing. It stops the viewport
// from snapping when text inputs are focused. Ionic handles this internally for
// a much nicer keyboard experience.
cordova.plugins.Keyboard.disableScroll(true);
}
if(window.StatusBar) {
StatusBar.styleDefault();
}
});
})
.controller('QuizController', ['$scope','$http','$sce',function($scope,$http,$sce){
$scope.score = 0;
$scope.activeQuestion = -1;
$scope.activeQuestionAnswered = 0;
$scope.percentage = 0;
/* Get stored data */
$http.get('quiz_data.json').then(function(quizData){
$scope.myQuestions = quizData.data;
/* Number of questions used in results */
$scope.totalQuestions = $scope.myQuestions.length;
});
$scope.selectAnswer = function(qIndex,aIndex) {
// Wheater or not the question is answered
var questionState = $scope.myQuestions[qIndex].questionState;
if( questionState != 'answered' ){
$scope.myQuestions[qIndex].selectedAnswer = aIndex;
// Check this selected answer based on what the user has clicked on
var correctAnswer = $scope.myQuestions[qIndex].correct;
$scope.myQuestions[qIndex].correctAnswer = correctAnswer;
if( aIndex === correctAnswer ){
$scope.myQuestions[qIndex].correctness = 'correct';
$scope.score += 1;
}else {
$scope.myQuestions[qIndex].correctness = 'incorrect';
}
$scope.myQuestions[qIndex].questionState = 'answered';
}
}
$scope.isSelected = function(qIndex,aIndex) {
return $scope.myQuestions[qIndex].selectedAnswer === aIndex;
}
$scope.isCorrect = function(qIndex,aIndex) {
return $scope.myQuestions[qIndex].correctAnswer === aIndex;
}
$scope.selectContinue = function(){
return $scope.activeQuestion += 1;
}
}]);
If you require the index.html, it can be found below:
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<meta name="viewport" content="initial-scale=1, maximum-scale=1, user-scalable=no, width=device-width">
<title></title>
<link href="lib/ionic/css/ionic.css" rel="stylesheet">
<link href="css/style.css" rel="stylesheet">
<!-- IF using Sass (run gulp sass first), then uncomment below and remove the CSS includes above
<link href="css/ionic.app.css" rel="stylesheet">
-->
<!-- ionic/angularjs js -->
<script src="lib/ionic/js/ionic.bundle.js"></script>
<!-- cordova script (this will be a 404 during development) -->
<script src="cordova.js"></script>
<!-- your app's js -->
<script src="js/app.js"></script>
</head>
<body ng-app="starter" ng-controller="QuizController">
<ion-pane>
<ion-header-bar class="bar-stable">
<h1 class="title">Home</h1>
</ion-header-bar>
<ion-content>
<h1>Test Your Knowledge</h1>
<div class="progress">
<div class=" {{ ($index === activeQuestion) ? 'on' : 'off' }} " ng-repeat="myQuestion in myQuestions"></div>
</div>
<!-- Inline conditional JS statement:
If the activeQuestion greater than 1 -->
<div class="intro {{ (activeQuestion > -1) ? 'inactive' : 'active' }}">
<h2>Welcome</h2>
<p>Click begin to test your knowledge of Saturn.</p>
<!-- activeQuestion variable will be set to 0 -->
<p class="btn" ng-click="activeQuestion = 0">Begin</p>
</div>
<!-- Array of questions -->
<div class="question
<!-- inline conditional statement -->
{{ $index === activeQuestion ? 'active' : 'inactive' }}
{{ myQuestion.questionState === 'answered' ? 'answered' : 'unanswered' }}
" ng-repeat="myQuestion in myQuestions">
<p class="txt">{{myQuestion.question}}</p>
<!-- Array of possible answers -->
<p class="ans"
ng-class="{
selected: isSelected($parent.$index, $index),
correct: isCorrect($parent.$index, $index)
}"
ng-click="selectAnswer($parent.$index, $index)"
ng-repeat="Answer in myQuestions[$index].answers">
{{Answer.text}}
</p>
<div class="feedback">
<p ng-show="myQuestion.correctness === 'correct'">You are <strong>correct</strong>.</p>
<p ng-show="myQuestion.correctness === 'incorrect'">Oops! That is not correct.</p>
<p>{{ myQuestion.feedback }}</p>
<div class="btn" ng-click="selectContinue()">Continue</div>
</div>
</div>
<div class="results">
<h3>Results</h3>
<p>You scored x% by corretly answering x of the total x questions. </p>
</div>
</ion-content>
<div class="tabs tabs-icon-top">
<a class="tab-item">
<i class="icon ion-home"></i>
Home
</a>
<a class="tab-item">
<i class="icon ion-star"></i>
Lesson
</a>
<a class="tab-item">
<i class="icon ion-gear-a"></i>
Quiz
</a>
</div>
</ion-pane>
</body>
</html>
style.css:
/* Empty. Add your own CSS if you like */
@import url(http://fonts.googleapis.com/css?family=Titillium+Web:900|Roboto:400,100);
body { background-color: #fff; padding: 20px; }
/* Main Container
=================== */
.scroll-content {
font-family: 'Roboto', sans-serif; font-size: 16px; font-weight: 400;
/* width: 650px; height: 650px; */
position: relative; /* Others -absolute positinoed- will get position in relation to this position */
overflow: hidden; /* anything outside of myQuiz container will be clipped or masked */
color: #fff;
background-color: #1abc9c;
}
.scroll-content h2 {font-size: 3em; margin: 0px; font-weight: 100; }
.scroll-content h3 {font-size: 2.4em; margin: 0px; font-weight: 100; }
.scroll-content p { margin: 0px 0px 14px 0px; }
.scroll-content .btn {
display: inline-block; cursor: pointer; background-color: red;
color: #fff; text-decoration: none;
padding: 5px 15px; border-radius: 6px;
}
.scroll-content h1 {
font-weight: 100; font-size: 2em; text-transform: uppercase; margin: 0px;
position: absolute; top: 25px; left: 36px;
}
/* Progress Bar */
.scroll-content .progress {
width: 550px; position: absolute; top: 160px; left: 40px;
}
.scroll-content .progress div {
position: relative; display: inline-block; width: 30px; height: 30px; margin-right: 30px;
border-radius: 50%; background-color: rgba(225,225,225,.2); transition: background-color 1s;
}
.scroll-content .progress div.on,
.scroll-content .progress div.answered {
background-color: #efbe5e;
}
/* Intro */
.scroll-content .intro { position: absolute; top: 225px; left: 2660px; width: 550px; }
.scroll-content .intro p { margin: 0px 0px 40px 0px; }
/* Questions */
.scroll-content .question {
width:550px; position: absolute; top: 225px; left: 2660px;
}
.scroll-content .question .txt {
font-size: 1.6em; margin: 0px 0px 20px 0px;
}
.scroll-content .question .ans {
display: inline-block; font-size: 1.1em; width: 225px; border: 2px solid rgba(238,189,102,.4);
border-radius: 6px; padding: 10px; margin: 0px 15px 15px 0px; position: relative;
}
.scroll-content .question .ans.selected {
border-color: #be4b16;
}
.scroll-content .question .ans.correct {
border-color: #459a2e;
}
.scroll-content .question .ans::after {
content:''; display: block; width: 40px; height: 40px;
background: no-repeat: 0px 0px; background-size: 40px 40px;
position: absolute; top: 5px; right: 5px;
}
.scroll-content .question .ans.selected::after {
background-image: url(../img/close-circled.png)
}
.scroll-content .question .ans.correct::after {
background-image: url(../img/checkmark-circled.png)
}
.scroll-content .question .ans.selected::after {
background-image: url(../img/close-circled.png)
}
.scroll-content .ans.correct::after {
background-image: url(../img/checkmark-circled.png)
}
.scroll-content .question.unanswered .ans {
cursor: pointer;
}
.scroll-content .question.unanswered .ans:hover {
background-color: mediumvioletred;
}
.scroll-content .question.answered .ans {
cursor: default;
}
/* Feedback */
.scroll-content .feedback {
color: #efbe5e; margin-top: 10px; transition: opacity 1.5s, margin-top 1.5s;
visibility: hidden; opacity: 0;
}
.scroll-content .feedback .btn {
margin-top; 5px;
}
.scroll-content .feedback strong {
color: #fff;
}
.scroll-content .answered .feedback {
visibility: visible; opacity: 1; margin-top: 10px;
}
/* Results */
.scroll-content .results {
position: absolute; top: 225px; left: 2660px; right: 40px;
}
.scroll-content .active, .scroll-content .inactive {
transition: left 1.5s ease-in-out;
}
.scroll-content .active {
left: 40px;
}
.scroll-content .intro.inactive, .scroll-content .inactive.answered { left: -1350px;}
.start-quiz {
margin: auto;
border: 3px solid green;
margin-top: 10px;
display: block;
}
.start-lesson {
margin: auto;
border: 3px solid green;
margin-top: 10px;
display: block;
}
.pane {
background-color: #3498db;
}
Why does ng-click not work?