PennController for IBEX › Forums › Support › Can we use template literals in Pcibex?
Tagged: template literals
- This topic has 5 replies, 2 voices, and was last updated 1 year, 3 months ago by
Jeremy.
-
AuthorPosts
-
May 9, 2023 at 1:38 pm #10536
Larissa_Cury
ParticipantHello!
I was wondering if we can use template literals in Pcibex, such as in the example below? In this case, I simply have a form and then I use the user’s input name and age value to salute he/she. I have 3 questions:
a) Can we use template literals in Pcibex in general?
b) Would I be able to do something like this as well.
c) We cannot use raw Js in Pcibex like storing a Js, a CSS and an HTML file, I suppose? So, for example, If I pasted the code below and upload the css and html files, it wouldn’t work, right? (https://doc.pcibex.net/how-to-guides/using-javascript/)Code:
*JS:
"use strict"; /// SELECT BUTTON: const btnSubmit = document.querySelector(".form__btn--submit"); // SELECT INPUT: const inputSubmitName = document.querySelector(".form__input--name"); const inputSubmitAge = document.querySelector(".form__input--age"); // SELECT BOX MESSAGE: let welcomeMsg = document.querySelector(".welcome"); // SELECT FORM DIV const formDiv = document.querySelector(".operation--welcome"); // SELECT AND MANIPULATE CONTENT: btnSubmit.addEventListener("click", function (e) { // Prevent default: e.preventDefault(); // Get name and age const name = inputSubmitName.value; const age = +inputSubmitAge.value; // transform string to a number // Make it disappear: formDiv.classList.add("welcome--hidden"); // Display Welcome User Message: welcomeMsg.classList.remove("welcome--hidden"); welcomeMsg.textContent = <code>Hello, ${name}! You are ${age} years old. Welcome! 🤗</code>; ////////////// HERE!! // log console.log(age, name); });
*CSS:
/* // trying to select the elemtns here // */ /* general properties of document */ * { margin: 0; padding: 0; box-sizing: inherit; } /* html { font-size: 62.5%; box-sizing: border-box; } */ body { font-family: "Poppins", sans-serif; font-weight: 300; color: yellow; /* cor do texto */ line-height: 1.9; background-color: #3616d9; /* cor do fundo */ } /* .first__image { width: 100px; border-radius: 50px; float: left; margin-right: 10px; } */ .form--title { position: absolute; left: 400px; height: 350px; width: 550px; bottom: 90px; } .form--personal__info { position: absolute; left: 300px; height: 350px; width: 550px; bottom: 50px; } .welcome-message { background-color: aquamarine; text-align: center; font-size: 30px; width: 100%; position: absolute; height: 80px; bottom: 280px; color: red; } .welcome--hidden { opacity: 0; transform: translate(20px, 20px); }
* HTML:
<!DOCTYPE html> <!-- doc-type declaration --> <html lang="en"> <head> <meta charset="UTF-8" /> <meta http-equiv="X-UA-Compatible" content="IE=edge" /> <meta name="viewport" content="width=device-width, initial-scale=1.0" /> <meta name="description" content="..." /> <link rel="stylesheet" href="style.css" /> <script defer src="script.js"></script> <title>My first form</title> <div class="operation operation--welcome"> <h2 class="form--title">Personal Info:</h2> <form class="form form--personal__info"> <input type="text" class="form__input form__input--name" placeholder="Your Name here"/> <input type="number" class="form__input form__input--age" placeholder="Your Age Here"/> <button class="form__btn form__btn--submit">→</button> <label class="form__label">Submit your data 👈</label> <!-- <label class="form__label">your data 👈</label> --> </form> </div> <div class = "welcome welcome-message welcome--hidden"> <h2 class="new--message">Welcome, user! 😀</h2> </div> </body> </head> </html>
-
This topic was modified 1 year, 3 months ago by
Larissa_Cury. Reason: editing code blocks
-
This topic was modified 1 year, 3 months ago by
Larissa_Cury.
-
This topic was modified 1 year, 3 months ago by
Larissa_Cury. Reason: editing clode blocks again
May 9, 2023 at 3:04 pm #10540Larissa_Cury
ParticipantAnother usage, can we do something like this?
Can we set a variable with const, let or var and reuse it? Ex:
// Set a variable: let time = 100 newTimer("timeout", time) .start() , newText("text",<code>you have ${time} to answer that! run!</code>) .center()
-
This reply was modified 1 year, 3 months ago by
Larissa_Cury. Reason: add another line of code
-
This reply was modified 1 year, 3 months ago by
Larissa_Cury.
May 10, 2023 at 5:49 am #10546Jeremy
KeymasterHello,
If you haven’t done so already, I invite you to read <the Core Concepts section in addition to the guide your reference, which also contains some pointers about the proper syntax and scope of PennController commands
I’ll start with your second message. All PennController commands are javascript functions. When you do
newTrial( /* ... */ )
whatever you write in place of/* ... */
are arguments to the functionnewTrial
. It is illegal in javascript to use thelet
keyword to define a variable as part as an argument, so you cannot do things likenewTrial( "myTrial", let time = 100 , newTimer("timeout", time) , /* ... */ )
. However, you can do things likenewTrial( "myTrial", time = 100 , newTimer("timeout", time) , /* ... */ )
because omittinglet
will make the expressiontime=100
return100
, which is a valid argument to pass to a function. Note that this would not settime
as a local variable, as in “in the scope ofnewTrial
“, because you simply are not in its scope (you’re just passing arguments)Now back to your first message. The files you upload to Resources are not just all thrown into the page when you open the experiment, otherwise it would be a real mess. What happens at the beginning of the experiment is your scripts get executed before
body
even gets populated, so any reference likedocument.querySelector(".form__btn--submit");
that you put at the root of your script will simply returnnull
. However, Ibex with its Message and Form controllers, and PennController withnewHtml
(ornewController
+ Message/Form) allow you to dynamically inject HTML files from the project’s Resources folder at some point during your experiment. The HTML files you upload to Resources can include CSS and javascript. However, the references in<link rel="stylesheet" href="style.css" />
and<script defer src="script.js"></script>
will fail on the farm, because the project’s files are not simply exposed at the local path. So you might want to include CSS + javascript in the HTML document, as in:<html lang="en"> <head> <meta charset="UTF-8" /> <meta http-equiv="X-UA-Compatible" content="IE=edge" /> <meta name="viewport" content="width=device-width, initial-scale=1.0" /> <meta name="description" content="..." /> <script> "use strict"; // embed code in an async function so as to wait for the button element to be added to the page const runScript = async () => { /// SELECT BUTTON: const btnSubmit = await new Promise(function getBtn(r) { const b = document.querySelector(".form__btn--submit"); if (b===null) window.requestAnimationFrame(()=>getBtn(r)); else r(b); }); // SELECT INPUT: const inputSubmitName = document.querySelector(".form__input--name"); const inputSubmitAge = document.querySelector(".form__input--age"); // SELECT BOX MESSAGE: let welcomeMsg = document.querySelector(".welcome"); // SELECT FORM DIV const formDiv = document.querySelector(".operation--welcome"); // SELECT AND MANIPULATE CONTENT: btnSubmit.addEventListener("click", function (e) { // Prevent default: e.preventDefault(); // Get name and age const name = inputSubmitName.value; const age = +inputSubmitAge.value; // transform string to a number // Make it disappear: formDiv.classList.add("welcome--hidden"); // Display Welcome User Message: welcomeMsg.classList.remove("welcome--hidden"); welcomeMsg.textContent = `Hello, ${name}! You are ${age} years old. Welcome! 🤗`; ////////////// HERE!! // log console.log(age, name); }); }; runScript(); </script> <style> /* general properties of document */ * { margin: 0; padding: 0; box-sizing: inherit; } body { font-family: "Poppins", sans-serif; font-weight: 300; color: yellow; /* cor do texto */ line-height: 1.9; background-color: #3616d9; /* cor do fundo */ } .form--title { position: absolute; left: 400px; height: 350px; width: 550px; bottom: 90px; } .form--personal__info { position: absolute; left: 300px; height: 350px; width: 550px; bottom: 50px; } .welcome-message { background-color: aquamarine; text-align: center; font-size: 30px; width: 100%; position: absolute; height: 80px; bottom: 280px; color: red; } .welcome--hidden { opacity: 0; transform: translate(20px, 20px); } </style> <title>My first form</title> </head> <body> <div class="operation operation--welcome"> <h2 class="form--title">Personal Info:</h2> <form class="form form--personal__info"> <input type="text" class="form__input form__input--name" placeholder="Your Name here"/> <input type="number" class="form__input form__input--age" placeholder="Your Age Here"/> <button class="form__btn form__btn--submit">→</button> <label class="form__label">Submit your data 👈</label> <!-- <label class="form__label">your data 👈</label> --> </form> </div> <div class = "welcome welcome-message welcome--hidden"> <h2 class="new--message">Welcome, user! 😀</h2> </div> </body> </html>
Note that the CSS rules will come after those already in place by Ibex + PennController, so you will want to adapt them (in particular, the
position:absolute;
shifts your content outside the visible portion of the page)Then you can do something like this:
newTrial( newHtml("my_file.html").print() , newButton("Next") .print() .wait() )
Jeremy
May 10, 2023 at 8:06 am #10551Larissa_Cury
ParticipantHi, Jeremy! Thank you very much! I’ll dig in into your answer, thanks! One more thing, I’d like to use a template literal to salute my participant. I thought thatr ‘var’ was a global variable, but I cannot do things such as
newText('salute',
hi, ${ID})
Why is that? How can I ‘use’ the ID var?
I was able to do sth as:
let welcomeMsg = 'maria' // 👉 Instructions trial newTrial("instructions", defaultText .center() .print() newText("instructions-1", <code>hi, ${welcomeMsg}</code>) )
just a note: I’m adding the template literals between ` , but the forum is formatting into a block code 🙂
-
This reply was modified 1 year, 3 months ago by
Larissa_Cury. Reason: editing my answer
May 10, 2023 at 8:13 am #10553Larissa_Cury
ParticipantLink to the experiment with the ID-Var element: https://farm.pcibex.net/r/wPASJJ/
May 11, 2023 at 2:13 am #10559Jeremy
KeymasterHi,
PennController elements do not correspond to any native javascript type, and in particular PennController Var elements do not correspond to javascript variables. As illustrated here, you can pass a Var element to the
text
command on a Text element to set its value dynamically. In your case, it would look something like this:newVar("hitext").set(getVar("ID")).set(v=>`hi, ${v}`), newText("instructions-1").text( getVar("hitext") )
Jeremy
-
This topic was modified 1 year, 3 months ago by
-
AuthorPosts
- You must be logged in to reply to this topic.