GREP: Apply to first instance only
Hi,
Another GREP question for you if you can help.
Situation is trying to apply a character style before a specific word, i.e. Applied Character Style "four".......
There are 4 words (lets call them: one, two, three, four) which are a common occurence and will always appear after the text that needs to have the applied character style, but my issue crops up when one of the four words appears twice or more times in one line and the GREP applies it to the 2nd or more instance of this word, i.e. Applied Character Style "one" random text "one"
I am using these greps in the same paragraph style:
^.*(?= one)
^.*(?= two)
^.*(?= three)
^.*(?= four)
I only want to have the GREP to apply to the first instance only - hope this stuff above makes sense?
Thanks
It's because GREP is greedy, by default.
The expression
^.*(something more)
will always grab as much characters as possible, before processing "something more": effectively, it will match anything up to the very last occurrence of that text.
You can instruct GREP to not match greedy by adding a '?' after the repeat command code:
^.*?(?=\b(one|two|three|four)\b)
-- the question mark can be added to each of the "repeat-this" codes: +, *, and ? ("!??" would mean: "match '!' zero or once, but uses the shortest match possible).
I condensed your list of four commands into one, because it seems to me that all of them would get matched in turn, leading to problems when you have both "one" and "two" in the same sentence. With your GREPs, first all up to "one" would get marked, then all up to "two". Mine uses 'whatever comes first'.
(I also added 'word boundaries' \b before and after, because you wouldn't want to match the 'one' in "Mr. Jones".)
Similar Messages
-
Interactive buttons on master pages only appearing on first instance in document [CS6]
I have a document being created for on-screen use that has next and previous buttons in the design. These buttons are on the master page with the 'On Click go to next/previous page' behaviour applied.
When the document is exported the buttons only appear on the first instance of that master page. IE. If pages 2-20 are created from that master, the buttons only appear on page 2.
I've seen other people reporting this problem in some other threads without an answer, so hopefully someone will see this who knows what the issue is.
I presume this is something to do with CS6, this is occuring in a document that was originally created in CS3 or 4. It's been revived for a new edition, and the buttons used to work perfectly under the old version, but now they're behaving as described. I've recreated them from scratch as well as using the previous version, but the results are the same.Wasn't there an Acrobat issue that affected this as well? Make sure that is updated, too.
While I'm on it, this is being viewed in Acrobat/Reader, right? Anything else, especially Mac Preview is a bit of crapshoot. -
I am trying to write a grep search for the first instance of a word in a paragraph.
How can I identify only the first instance of 'FREE' in a paragraph and apply a style to it, without also styling the 2nd or more instance of the word?
Thanks(?i)^(.+?)FREE should find the first instance in a paragraph. The (?i) makes the search case insensitive in case it wasn't typed as all caps, the ? inside the second grouping makes the shortest match for cases when there is more than one instance in a paragraph, and I've not added any quotes since I presumed those aren't actually in the text.
I would deal with the formatting by typing FREE exactly as you want it someplace on the pastebord, then copy to the clipboard. Change to $1~c which replaces the found string with the text found in the first subexpression (.+?), which is the stuff before the first FREE, and the the formatted contents of the clipboard for the FREE. -
Hide all instances of text fields, instead of only first instance?
Hi All, Been scouring looking for an answer to this, and tried several things that I haven't been able to make work for me.
I'm creating a quote form in LC Designer.
I've got buttons to add or remove instances of a subform. The subform contains 5 fields. I need to add a checkbox that will hide only 2 of the fields within the subform when checked, and when unchecked, show them again. I am able to make this work, but only for the first instance (instance 0?). How can I make this work so it hides these fields from each of the visible instances?
You can view the form at: https://workspaces.acrobat.com/?d=GVqRa5BfyIKxpkAVBxje3Q
For anyone that is feeling abitous, what I really wanted to do seems impossible, so I'm going with the above as a simpler workaround. What I really want to do is have a check box that when clicked, will hide the quotation form, and make the purchase order visible, carrying over any field data into a new table on the Purchase order form from the quote form. I've attached this form at https://workspaces.acrobat.com/?d=pqpsXx5VPi*LkMeVKrX57w
I understand that I need to create an XML schema to accomplish this, but can't figure out for the life of me how to actually create the schema. I can only find info on how to bind the data source once it's been created.
I would be forever grateful to get a hand with getting either of these forms to do what I need.
Thank you!Hi Barb,
The first question is fairly easy, you need do exactly what you were doing but for all the rows, so;
var newPresence = (this.rawValue == "1") ? "hidden" : "visible";
var rows = page1.resolveNodes("Subform2[*]");
for (var i = 0; i < rows.length; i++)
var row = rows.item(i);
row.Col2.presence = newPresence;
row.Col4.presence = newPresence;
The second one can be done, but is a bit fiddly. I have updated your sample, https://workspaces.acrobat.com/?d=jLYZGae--BiZ0khRbZqvuA
This relies on having two top level subforms, one for Sales_Quotation and one for Purchase_Order, when you click the checkbox the name of the top element in your data connection is updated, the form is remerged and rendered with the top level subform that matches the new name. Look in the hierarchy tab and you will see what I mean by top level subform. Any elements that have the same binding under the Sales_Quotation and Purchase_Order subforms will bind correctly. You wont need an XML Schema.
The fiddly bit is that in Designer you can only edit the first top level subform in the form, the second one wont show up at all at design time. However, the approach was discribed in this blog http://blogs.adobe.com/formfeed/2011/02/multiple-top-level-subforms.html and John has a macro to move the first subform become the last. I've already run the first macro, NewTopSubform, so you just need the RotateSubforms macro. There's more information on macros and how to install them in the Designer help http://help.adobe.com/en_US/enterpriseplatform/10.0/DesignerHelp/WS3041177a02dcf48e2f8c933 d12daa5a53a3-8000.html
Good luck
Bruce -
I am facing a problem with my iPhone 4. I applied the first syncing with outlook 2007 by choosing the "merge" option. At the end of the process, some contacts are correctly sync, but most are only sync with the names. Numbers are lost. Any suggestion?
I would love to do this as well. All I need is my calendar appts from outlook. Right now I am using google calendar sync, but I would like to move to the cloud and away from google. I find it hard to believe there isn't an option to do this.
-
Compare two columns and match ALL recurring values, not just the first instance
Hi everybody...
I was looking for a way to compare values in two columns, identifying every duplicate value instance on a third column.
Searching around the forums, I found a solution, albeit a partial one; I am using this formula: =IFERROR("Duplicate in row "&MATCH($A,$B,0),"") along column C, to compare values between columns A and B. When applied, the formula will render the first instance where there is a duplicate; unfortunately MATCH will only register the first instance of the duplicated values.
For example:
The first value on column A is 'Apple'. On column B there are three instances for the value 'Apple', the formula identifies the first of these values, but not the remaining two.
I am not an advanced Numbers or Excel user, and the answer to this problem eludes me. I am attempting to compare columns that have no less than 1000 rows each, so you can imagine how, finding a solution to my problem would be really great.
Thanks in advance,
PabloUnfortunately I can't see your screenshot, but supposing you have a table like this:
Col1
Col2
1
3
Dupe
2
4
Dupe
3
5
Dupe
4
6
5
7
Then here is one way to flag the duplicates.
The formula in C2, copied down, is:
=IF(COUNTIF($A,$B2)≥1,"Dupe","")
Then filter on column C for 'Dupe', and copy the values in column B to wherever you need them.
SG -
Grep to find first occurrence of a particular word in a story
Hello Grepers
I haven't had luck working out a Grep to find first / last occurrence of a particular word in a story.
To find the first occurrence of the word hello in a paragraph I would use this grep.
(Hello(?!=Hello*$))
For the last this works.
((?=Hello(?=.*Hello)))|(Hello(?!=Hello*$))
I have tried single line and multiline prefixes but they don't do the trick.
Waiting in suspence,
TrevorHi Marc,
Thanks for your reply, I'm glad you got my subtle hints.
1) First Hello in the paragraph(s)
Marc Autret wrote:
Also, it seems to me that the GREP patterns you've posted are wrong and only work by accident. For example:
(Hello(?!=Hello*$))
actually means: find 'Hello' if and only if the match is not followed by '=Hell' and 'o' zero or more times and an EOL.
Well Marc I made a Hell of a mistake!!!
I meant to write (Hello(?!=Hello.*$)) with a dot there which at least is not quite as stupid if not more correct.
In fact both (Hello(?!=$)) without a . and Hello(?!=^) work, well sort of work for the first Hello of the paragraph(s) depending on the were one start the search from (before the first Hello works otherwise it will find the next "first" Hello of the paragraph.
I said sort of because I naively presumed that GREP styles would work like GREPS, dumb hey.
I was really looking to use these GREPS in GREP styles, well you can't.
In a GREP style
(Hello(?!=$)) or any of its variants will apply the style to all occurrences of Hello in the paragraph.
I can partially circumvent this problem by adding a second GREP STYLE which applies an anti style to all words after the first Hello (?<=Hello).*
i.e. I have a want my first Hello to be bolded then set the first style for bold and the second to regular.
This however is not practical if one wants to auto style more than one word in this way in other words to do the same for the first Hi and the first Hello in the paragraph.
As a regular GREP solution providing that one starts the GREP search before the first occurrence of Hello It will work.
2 & 4) First and Last Hello in the story
Again these GREPs don't work using GREP styles, this I think is because GREP paragraph styles only look within the one paragraph at a time they are applied to. So they can't look at the preceding or following paragraphs to see if they contain Hello or not.
If I am correct I see no work around to this and am will to pay 10 Pounds, Euros or Dollars to whoever comes up with a non-script fully functional GREP styles solution for this (I think my money's safe)
Regarding the regular non styled GREPs they nearly work as stated.
When (?s)(Hello)(?!.*?\1) is used to find the last occurrence of Hello in the story, if the find tab is used it will firstly find the last Hello of the story then it will go back and find the one before that!! then it will go onto the next story.
Using the GREP in script works as stated.
The easiest way of course to find the first and last Hello in a story, document etc. by script would be
app.findGrepPreferences.findWhat = Hello"
myFinds = myWhatEver.findGrep();
First occurrence myFinds[0], last occurrence myFinds[-1].
HOWEVER NOT PARTICULARLY EFFICIENT!
3) Last occurrence of Hello in paragraph.
This one works perfectly both with regular GREPS and GREP styles.
In summary
GREP STYLES: only the (Hello)(?!.*?\1) last Hello in the paragraph GREP works.
GREP FIND TAB: the first Hello in the paragraph GREP finds the first Hello after the cursor, the first in the story works in the limited way as written, last in story has the problem of finding the second last Hello after finding the last Hello, Last in paragraph works flawlessly.
GREP SCRIPTING: all work without problem except for the first Hello in the story that has the problem of needing to extract the last 5 letters which for my automatic text / GREP changer is a bit of a problem but for general scripting would not be problematic.
Once again Marc thanks for your input, I doubt there's much if anything to add on the topic maybe Laurent Tournie from indigrep.com might have some ideas. I don't know his contact details so if you think it's a good idea please can you send him a tweet / mail.
Regards
Trevor -
Hi Everyone
I want to create return but linked to original sales order where the material was delivered in the first instance, I don’t want to create other sales order (to return) with references to the original, and then other sales order to be delivered again (replacement).
Example
SALES
1. Create a sales order number 33 with 10 Ton
2. The delivery is linked to sales order 33 just with 8 Ton
3. Invoice is created linked to the delivery with 8 Ton
4. Sales order number 10 pending qty is 2 Ton
RETURN
5. We would like to link the return delivery to the sales order, 5 Tons will be retuned
6. Credit memo is created
7. Sales order number 10 pending qty update to 7 TonThe only way is to change the item categories in the delivery.
Create the delivery wrt the original sales order.
Change the item category(In the config make sure the return is checked)- But I think you need to do some changes in the user exit to enable the item category in the delivery)..
The other option is to have a return order document(type RE) and then create the return delivery for this document. In the copy controls you can maintain the return item categories while creating the return order from sales order..
Thanks -
XControls Annoyance - 'Apply Changes to Instances'
Hello,
I've been working with XControls a little, I find them a nice little way of displaying my class data...
However, I have this problem that when I load my project, I have to click 'Apply changes to instances' (as you can hopefully see in the picture) before I can run any of my VIs. Elsewise there are simply broken run arrows in my VIs.
It doesn't make a difference if I apply then save my project and re-open.
It seems to effect all my XControls but not always at once. The problem consistent if I open a project, close it and open back up but if I work on the project, save then come back, sometimes its the same ones sometimes its different ones...I can't spot any predictable behaviour ...
Maybe I'm missing something silly or someone else has come across this?
LabVIEW 2012 btw
Many Thanks
NickHi Nick,
Welcome to the NI Discussion Forums, thanks for your post.
I haven't had this particular myself, but would like to investigate what is causing this. Does this happen with every XControl in any project? Or just this one?
If this only happens for this project (or similar ones) would you mind attaching the project in a reply?
Regards,
Ben Clark -
We need to apply object style to only eps files in doc, or tif.... How to do this? Maybe someone have a script?
thanks@kajzica – I don't have a script for that, but it is scriptable. You surely mean that you want to apply the object styles to the container frame of the images, aren't you?
A few minutes later – try the following ExtendScript (JavaScript) code:
You could edit the names of the two object styles at the beginning of the script code.
OR: you could first run the script, the script will add two object styles to the document that you can edit afterwards.
The script will sort the EPS and the TIFs from the other image types.
Make sure that all graphics are up-to-date and linked correctly!!
//ApplyObjectStylesTo_ContainersOf_TIF_EPS.jsx
//Uwe Laubender
* @@@BUILDINFO@@@ ApplyObjectStylesTo_ContainersOf_TIF_EPS.jsx !Version! Thu Dec 12 2013 13:15:30 GMT+0100
//Edit your style names here. Change the name between the two " " only!!
//OR: edit your object styles in InDesign after running the script.
var styleNameForEPS = "EPS-Containers-Only";
var styleNameForTIF = "TIF-Containers-Only";
app.scriptPreferences.userInteractionLevel = UserInteractionLevels.interactWithAll;
app.doScript(_ApplyObjectStylesToContainers, ScriptLanguage.JAVASCRIPT, [], UndoModes.ENTIRE_SCRIPT, "Apply object styles to containers for TIF and EPS graphics");
function _ApplyObjectStylesToContainers(){
var d=app.documents[0];
var allGraphicsArray = d.allGraphics;
if(!d.objectStyles.itemByName(styleNameForEPS).isValid){
d.objectStyles.add({name:styleNameForEPS});
if(!d.objectStyles.itemByName(styleNameForTIF).isValid){
d.objectStyles.add({name:styleNameForTIF});
for(var n=0;n<allGraphicsArray.length;n++){
//The EPS case:
if(allGraphicsArray[n].getElements()[0].constructor.name === "EPS"){
allGraphicsArray[n].parent.appliedObjectStyle = d.objectStyles.itemByName(styleNameForEPS);
//The TIF case
if(allGraphicsArray[n].getElements()[0].constructor.name === "Image" && allGraphicsArray[n].getElements()[0].imageTypeName === "TIFF"){
allGraphicsArray[n].parent.appliedObjectStyle = d.objectStyles.itemByName(styleNameForTIF);
}; //END: function _ApplyObjectStylesToContainers()
Uwe -
GetSelectedIndex() to return position selected, not first instance?
Hi
I am having trouble getting the correct index from a JComboBox. My program's JComboBox stores duplicated entries.
When the getSelectedIndex() method is used, it returns the index of the FIRST instance of the object that was selected!!! instead of returning the index to the actual item selected by the mouse!!
* I need this labelIndex to be the index of the position selected!! not the
* first instance of the label in the list.
labelIndex = frame.labelsComboBox.getSelectedIndex();
Does anyone know how to remedy this?Instead of putting Strings in your combobox, put some other kind of Object which has a toString() method which returns the string you want to show. Then when the JComboBox code calls the equals() method (I think) to see which index matches, it will only find the correct one.import java.awt.*;
import java.awt.event.*;
import javax.swing.*;
public class Test2 extends JFrame {
public Test2() {
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
Container content = getContentPane();
MyObject[] stuff = { new MyObject("A"),new MyObject("B"), new MyObject("A")};
JComboBox jcb = new JComboBox(stuff);
content.add(jcb, BorderLayout.NORTH);
jcb.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent ae) {
System.out.println(((JComboBox)ae.getSource()).getSelectedIndex());
setSize(200,200);
public static void main(String[] args) { new Test2().setVisible(true); }
class MyObject {
String text;
public MyObject(String text) { this.text=text; }
public String toString() { return text; }
}This example uses the default Object equals() method which is actually ==. You can override equals() if you want.
I use this a lot to put any kind of object in a combo. -
Global RegExp Stops At First Instance
I'm having some trouble getting a global RegExp to actually go global.
It's testing great at RegExr.com, but when I run it in my actual code, it stops after the first instance. Here's my code.
var strongRegExp:RegExp = /<h3><a title="(.*)" href="(.*)">(.*)<\/a><\/h3>/g;
var matches:Object = strongRegExp.exec(loader.data);
for( var i:String in matches ) {
if (i != "input") {
trace( i + ": " + matches[i] );
Why is this stopping at the first instance? Is it something to do with my loop?Yes, I do mean that the regex doesn't catch all matches, only the first.
Here's a sample that includes two items it should catch.
<div class="title">
<h3><a title="SEO Article - SEO Optimize Your Website. Free SEO / Search Engine Optimization Lessons / Video. Need Help?" href="http://www.articlesbase.com/marketing-tips-articles/seo-article-seo-optimize-your-website- free-seo-search-engine-optimization-lessons-video-need-help-1268075.html">SEO Article - SEO Optimize Your Website. Free SEO / Search Engine Optimization Lessons / Video. Need Help?</a></h3>
</div>
<div class="title">
<h3><a title="Are You Actually Paying For SEO?" href="http://www.articlesbase.com/seo-articles/are-you-actually-paying-for-seo-3742716.html">Are You Actually Paying For SEO?</a></h3>
</div>
The regex should be able to capture both <h3> tags in their entirety and give me access to the title, the href, and the anchor text.
At least, that's what I'm after. -
Why is my ping so high in the first column only when i do a tracert?
When i do a tracert my ping is really high in the first column only on each hop and then it drops to a respectable level. Does anyone know why it is like this on my 4G LTE device? On my dsl when i do the same ping test its pretty even across on each hop. This is what im seeing when i do a ping test on my 4G LTE device.
tracert www.yahoo.com
Tracing route to ds-any-fp3-real.wa1.b.yahoo.com [98.139.183.24]
over a maximum of 30 hops:
1 9 ms 3 ms 3 ms
2 1101 ms 34 ms 38 ms 193.sub-66-174-20.myvzw.com [66.174.20.193]
3 169 ms 55 ms 52 ms 49.sub-69-83-13.myvzw.com [69.83.13.49]
4 52 ms 56 ms 54 ms 194.sub-69-83-13.myvzw.com [69.83.13.194]
5 179 ms 58 ms 57 ms 101.sub-66-174-17.myvzw.com [66.174.17.101]
6 168 ms 57 ms 60 ms TenGigE0-0-1-0.GW14.BOS4.ALTER.NET [152.179.2.97
7 181 ms 58 ms 57 ms 0.ge-0-3-0.XL3.BOS4.ALTER.NET [152.63.17.130]
8 170 ms 59 ms 58 ms 0.ae3.BR1.NYC1.ALTER.NET [152.63.18.222]
9 177 ms 67 ms 59 ms ae11.edge2.NewYork.Level3.net [4.68.62.41]
10 * * * Request timed out.
11 * * * Request timed out.
12 * * * Request timed out.
13 192 ms 49 ms 60 ms ae-4-90.edge4.NewYork1.Level3.net [4.69.155.210]
14 185 ms 51 ms 60 ms YAHOO-INC.edge4.NewYork1.Level3.net [4.28.130.82
15 380 ms 73 ms 129 ms ae-5.pat2.bfz.yahoo.com [216.115.96.67]
16 339 ms 69 ms 146 ms ae-4.msr2.bf1.yahoo.com [216.115.100.73]
17 215 ms 152 ms 80 ms xe-5-0-0.clr2-a-gdc.bf1.yahoo.com [98.139.128.11
18 289 ms 217 ms 217 ms et-17-1.fab6-1-gdc.bf1.yahoo.com [98.139.128.47]
19 187 ms 87 ms 79 ms po-14.bas2-7-prd.bf1.yahoo.com [98.139.129.227]
20 474 ms 314 ms 294 ms ir2.fp.vip.bf1.yahoo.com [98.139.183.24]
Trace complete.hi there
see you never got an answer from vzw
take it you still have the high ping or no ping in my cases
your doing better then i
seems the lte is getting bad with this problem over time as my connection times out causing half loaded web pages and lots of buffering in video playback
i have had 3 tickets in the past 3 month to try and get this fixed but they say cant find anything wrong
and noone else is having the problem here are a few things that seems to have helped me out
1 increase your TTL time till live
this tells your computer to wait a bit longer before giving up and requesting that a packet of info be resent
2 in your computers network settings and reg you can change packet size to a smaller number and add a stop bit to the packet with a time stamp on each packet back in the old days this was what v 90 modems did to get v92 speeds and did help with noisy copper wire dial up and seems to help here too
http://www.dslreports.com/drtcp
is a tool that will help you change your computer setting and reg
use drtcp and the results from this page
http://www.dslreports.com/tweaks
xp win 7 win 8 this will help. vista did it right and dynamically change these settings on the fly and all of step 2 is unnecessary
remember your original settings write them down so you can go back to them should you have problems
also make a restore point and backup your reg before tinkering with windows os
send a private message to me if you need more help or get a computer savvy friend to help you out if you need
3 if your signal noise is under 4G -100bd the lower the better, there is a way to set your android to lte only mode.
more likely to lose data and voice in weak signal areas but great if tethering or hotspotting at home
dail *#*#4636#*#* this is a back door to your android software and is open source code by android os not vzw
and will not unlock your phone voiding warranties. be warned though if you set things wrong in here
you can make more problems be very sure what you change and do one thing at a time so you remember and can dial in again and change it back should you disable something you need. fyi each time you dial in the number it resets to vzw default setting and may look like it did not save setting but it doz. till you dial in again.
good luck
ron
ps im not a vzw rep in any way other then a fellow customer not getting answers. -
Mobile Accounts: Sync new accounts first time only.
When a user logs into a computer for the first time it is set to create a mobile account, however we don't use home directory syncing because the typical size of our 200 users' home directories is over 100Gb which makes syncing home directories not viable.
It would be very handy, though, to have it sync the first time only at login so that our user directory template is automatically copied over which will save a lot of time setting up new users.
Accoring to Apple's User Management v10.5 documentation on page 203:
+"To initially sync local and network homes so that the network home folder replaces the local home folder, choose “Create home with default sync settings."+
(This refers to Workgroup Manger -> Preferences -> the Mobility pane -> Account Creation -> Creation tab)
After testing, though, it is quite clear that this does not work - at least on my setup. I can get it to work by going to the Rules tab in the Mobility pane and ticking the sync at login and logout, but this syncs every time on both login and logout, which is not what I want to achieve.
Any ideas?I also mentioned, that some Safari-Extensions I installed on the iMac are missing now on my iMac-Profile. I also mentioned, that some settings for 1Password are reset to default values.
-
The first instance is running on a Sun R420 Enterprise
server. The second instance will run in the same server.When you say "Authorized" you mean in the sense of Itunes Store Authorized? if so the system in Question is authorized it is my primary Workstation and was waiting until iCloud came out to update to Lion. My MBP , and 2006 MP are all running Lion and are part of the 5 systems "authorized". I did not run into this issue with either the MBP or the MP when i installed and I bought two copies at the same time on my the first day Lion was available.
Do you know the mechanism with which the App Store tracks purchases on different computers prior to iCloud coming out?
once again thanks for your response
chris meredith
Maybe you are looking for
-
Thunderbird puts a new message at the end of the thread. Is there any way of changing this preference so that new messages are displayed at the top of the thread. This is is more logical. You need to see new message in thread directly, rather than sc
-
Printing starts at bottom of page
starts printing at bottom of page
-
Help! I tried to access my "Sent Mail" folder this morning and all messages are GONE. I read through the earlier posts, and didn't get anywhere because I don't have a "Mail" folder in my Library folder. Yesterday I did a bunch of upgrades, included t
-
Hi Lincoln. Please can you send me some documentation on any topic of SAP HR like ESS,PA,PM etc. to [email protected] Thanks in advance for sending a lot for the documents. Phanikumar
-
Running TiBook as displayless server....
Hi, with the addition of a MacBook in our house, our old TiBook is looking for a new job. I'd like to use the TiBook with its lid closed, and no keyboard, mouse, or external display attached. I had the machine running lid-closed, attached to keyboard