@react-navigation/native#useRoute JavaScript Examples

The following examples show how to use @react-navigation/native#useRoute. You can vote up the ones you like or vote down the ones you don't like, and go to the original project or source file by following the links above each example. You may check out the related API usage on the sidebar.
Example #1
Source File: HomeStack.js    From designcode-app with MIT License 6 votes vote down vote up
export default function HomeStack() {
  const route = useRoute();
  const navigation = useNavigation();

  if (route.state && route.state.index > 0) {
    navigation.setOptions({ tabBarVisible: false });
  } else {
    navigation.setOptions({ tabBarVisible: true });
  }

  return (
    <Stack.Navigator
      screenOptions={{
        headerShown: false,
      }}
      mode="modal"
    >
      <Stack.Screen name="Home" component={Home} />
      <Stack.Screen name="Section" component={Section} />
      <Stack.Screen name="Video" component={VideoScreen} />
    </Stack.Navigator>
  );
}
Example #2
Source File: MovieRecommendations.js    From MoviesDaily with MIT License 6 votes vote down vote up
MovieRecommendations = ({ recommendations, navigation }) => {
  const movieData = recommendations.results.slice(0, 10);
  const route = useRoute().name;

  if (movieData.length === 0) return null;

  return (
    <View>
      <Text style={Styles.titleText}>Recommendations</Text>
      <FlatList
        keyExtractor={(item) => item.id.toString()}
        data={movieData}
        renderItem={({ item }) => Recommendations(item, navigation, route)}
        horizontal
        showsHorizontalScrollIndicator={false}
      />
    </View>
  );
}
Example #3
Source File: Page.js    From Legacy with Mozilla Public License 2.0 5 votes vote down vote up
function UserActivityPage({ toggleDrawer, filters }) {
  var moment = useMoment();
  var theme = useSelector(i => i.themes[i.theme]);
  var date = moment().tz('America/Chicago');
  var dateString = `${date.year()}-${(date.month() + 1).toString().padStart(2, '0')}-${(date.date()).toString().padStart(2, '0')}`
  var route = useRoute();
  if (route.params.date) {
    dateString = route.params.date;
  }
  var username = route.params.username
  var userdata = useAPIRequest({
    endpoint: 'user',
    data: { username }
  })
  let user_id = userdata?.user_id
  var dataraw = useAPIRequest(user_id ? {
    endpoint: 'user/activity',
    data: { day: dateString, user_id },
    cuppazee: true
  } : null)
  if (!dataraw) return (
    <View style={{ flex: 1, alignContent: "center", justifyContent: "center", backgroundColor: theme.page.bg }}>
      <ActivityIndicator size="large" color={theme.page.fg} />
    </View>
  )
  var activityList = ActivityConverter(dataraw, filters, userdata);
  return <View style={{ flex: 1 }}>
    <FlatList
      contentContainerStyle={{ width: 500, maxWidth: "100%", alignItems: "stretch", flexDirection: "column", alignSelf: "center", paddingBottom: 88 }}
      style={{ flex: 1, backgroundColor: theme.page.bg }}
      extraData={[userdata?.username]}
      ListHeaderComponent={<View>
        <View style={{ padding: 4 }}>
          <Card noPad>
            <DateSwitcher dateString={dateString} toggleDrawer={toggleDrawer} />
            <ActivityOverview date={dateString} user_id={user_id} filters={filters} />
          </Card>
        </View>
      </View>}
      // getItemLayout={(data, index) => (
      //   { length: data.height||0, offset: data.offset||0, index }
      // )}
      data={activityList.sort((a, b) => new Date(b.time) - new Date(a.time))}
      renderItem={({ item: act }) => <ListItem act={act} userdata={userdata} />}
      keyExtractor={(item, index) => item.key}
    />
    <UserFAB username={username} user_id={user_id} />
  </View>
}
Example #4
Source File: LastPeriodScreen.js    From ovuli with MIT License 5 votes vote down vote up
LastPeriodScreen = () => {
  const [selectedDate, setSelectedDate] = React.useState(null);
  const navigation = useNavigation();
  const route = useRoute();
  const saveLastPeriod = () => {
    try {
      AsyncStorage.setItem('lastPeriod', selectedDate.toISOString());
    } catch (error) {
      console.log(error);
    }

    if (route.params.prevScreen == 'DoYouKnow') {
      navigation.navigate('SecondLastPeriod');
    }
    if (route.params.prevScreen == 'AverageCycle') {
      navigation.navigate('Dashboard');
    }
  };

  return (
    <View style={styles.container}>
      <StatusBar hidden />
      <Image style={styles.topImage} source={TopImage} />
      <View style={{ padding: 20, alignSelf: 'flex-start' }}>
        <Text style={styles.nameText}>{i18n.t('when_was_your_last_period')}</Text>
      </View>

      <View style={styles.calenderContainer}>
        <CalendarPicker
          onDateChange={date => setSelectedDate(date)}
          startFromMonday={true}
          previousTitle=""
          nextTitle=""
          headingLevel={0}
          weekdays={CALENDAR_WEEK_DAYS}
          dayOfWeekStyles={styles.dayOfWeekStyles}
          selectedDayStyle={styles.selectedDate}
          selectedDayTextColor="#fff"
        />
      </View>
      <TouchableOpacity style={styles.button} onPress={saveLastPeriod}>
        <View style={styles.buttonTextContainer}>
          <Text style={styles.buttonText}>{i18n.t('continue')}</Text>
          <AntDesign style={styles.arrowIcon} name="arrowright" size={18} />
        </View>
      </TouchableOpacity>
    </View>
  );
}
Example #5
Source File: index.js    From semana-omnistack-11 with MIT License 5 votes vote down vote up
export default function Detail() {
  const navigation = useNavigation();
  const route = useRoute();

  const incident = route.params.incident;
  const message = `Olá ${incident.name}, estou entrando em contato pois gostaria de ajudar no caso "${incident.title}" com o valor de ${Intl.NumberFormat('pt-BR', { style: 'currency', currency: 'BRL' }).format(incident.value)}`;

  function navigateBack() {
    navigation.goBack()
  }

  function sendMail() {
    MailComposer.composeAsync({
      subject: `Herói do caso: ${incident.title}`,
      recipients: [incident.email],
      body: message,
    })
  }

  function sendWhatsapp() {
    Linking.openURL(`whatsapp://send?phone=${incident.whatsapp}&text=${message}`);
  }

  return (
    <View style={styles.container}>
      <View style={styles.header}>
        <Image source={logoImg} />

        <TouchableOpacity onPress={navigateBack}>
          <Feather name="arrow-left" size={28} color="#E82041" />
        </TouchableOpacity>
      </View>

      <View style={styles.incident}>
        <Text style={[styles.incidentProperty, { marginTop: 0 }]}>ONG:</Text>
        <Text style={styles.incidentValue}>{incident.name} de {incident.city}/{incident.uf}</Text>

        <Text style={styles.incidentProperty}>CASO:</Text>
        <Text style={styles.incidentValue}>{incident.title}</Text>

        <Text style={styles.incidentProperty}>VALOR:</Text>
        <Text style={styles.incidentValue}>
          {Intl.NumberFormat('pt-BR', { 
            style: 'currency', 
            currency: 'BRL' 
          }).format(incident.value)}
        </Text>
      </View>

      <View style={styles.contactBox}>
        <Text style={styles.heroTitle}>Salve o dia!</Text>
        <Text style={styles.heroTitle}>Seja o herói desse caso.</Text>

        <Text style={styles.heroDescription}>Entre em contato:</Text>

        <View style={styles.actions}>
          <TouchableOpacity style={styles.action} onPress={sendWhatsapp}>
            <Text style={styles.actionText}>WhatsApp</Text>
          </TouchableOpacity>

          <TouchableOpacity style={styles.action} onPress={sendMail}>
            <Text style={styles.actionText}>E-mail</Text>
          </TouchableOpacity>
        </View>
      </View>
    </View>
  );
}
Example #6
Source File: usePlatformParams.native.js    From polaris with Apache License 2.0 5 votes vote down vote up
usePlatformParams = () => {
  const nativeRoute = useRoute()
  return nativeRoute.params || {}
}
Example #7
Source File: usePlatformLocation.native.js    From polaris with Apache License 2.0 5 votes vote down vote up
usePlatformLocation = () => {
  const { routes } = useContext(RoutesContext)
  const nativeRoute = useRoute()
  const currentRoute = routes.find(route => route.path === nativeRoute.name)
  return { currentRoute, params: nativeRoute.params || {} }
}
Example #8
Source File: index.js    From be-the-hero with MIT License 5 votes vote down vote up
export default function Details() {
  const navigation = useNavigation()
  const route = useRoute()

  const incident = route.params.incident
  const messageToSend = `Olá ${incident.name}, estou entrando em contato pois gostaria de ajudar no caso "${incident.title}" com o valor de R$ ${
    Intl.NumberFormat('pt-BR', {
      style: 'currency',
      currency: 'BRL' }
    ).format(incident.value)
  }` 

  function navigateBack() {
    navigation.goBack()
  }

  function sendEmail() {
    MailComposer.composeAsync({
      subject: `Herói do caso: ${incident.title}`,
      recipients: [ incident.email ],
      body: messageToSend
    })
  }

  function sendWhatsapp() {
    Linking.openURL(`whatsapp://send?phone=${incident.whatsapp}&text=${messageToSend}`)
  }

  return (
    <View style={ styles.detailsContainer }>

      <View style={ styles.headerContainer }>
        <Image source={ logoImage }/>

        <TouchableOpacity style={ styles.headerButton } onPress={ navigateBack }>
          <Feather name="arrow-left" size={ 28 } color="#E02041"/>
          <Text style={ styles.headerButtonText }>Voltar</Text>
        </TouchableOpacity>
      </View>

      <View style={ styles.incident }>
        <Text style={ styles.incidentOng }>
          { incident.name } de { incident.city }/{ incident.uf }
        </Text>

        <Text style={ styles.incidentDescription }>
          { incident.description }
        </Text>

        <Text style={ styles.incidentValue }>
        {
          Intl.NumberFormat('pt-BR', {
            style: 'currency',
            currency: 'BRL' }
          ).format(incident.value)
        }
        </Text>
      </View>

      <View style={ styles.contact }>
        <Text style={ styles.heroTitle }>Salve o dia!</Text>
        <Text style={ styles.heroTitle }>Seja o herói desse caso</Text>

        <Text style={ styles.heroDescription }> Entre em contato:</Text>
        <View style={ styles.contactButtons }>
          <TouchableOpacity onPress={ sendWhatsapp } style={ styles.buttonWhatsapp }>
            <FontAwesome name="whatsapp" size={ 32 } color="#E9FAEF"/>
            <Text style={[ styles.buttonText, styles.buttonTextWhatsapp ]}>Whatsapp</Text>
          </TouchableOpacity>

          <TouchableOpacity onPress={ sendEmail } style={ styles.buttonEmail }>
            <FontAwesome name="envelope-o" size={ 30 } color="#FBE8EC"/>
            <Text style={[ styles.buttonText, styles.buttonTextEmail ]}>E-mail</Text>
          </TouchableOpacity>
        </View>
      </View>
    </View>
  )
}
Example #9
Source File: index.js    From designcode-app with MIT License 5 votes vote down vote up
function Section() {
  const navigation = useNavigation();
  const route = useRoute();
  const section = route.params.section;

  useEffect(() => {
    StatusBar.setBarStyle("light-content", true);

    return StatusBar.setBarStyle("dark-content", true);
  }, []);

  return (
    <>
      <ScrollContainer>
        <Container>
          <Cover>
            <Image source={section.image} />
            <PlayWrapper>
              <TouchableOpacity
                underlayColor="transparent"
                onPress={() => {
                  navigation.navigate("Video");
                }}
              >
                <PlayView>
                  <PlayIcon style={{ marginLeft: -10 }} />
                </PlayView>
              </TouchableOpacity>
            </PlayWrapper>
            <Wrapper>
              <Logo source={section.logo} />
              <Subtitle>{section.subtitle}</Subtitle>
            </Wrapper>
            <Title>{section.title}</Title>
            <Caption>{section.caption}</Caption>
          </Cover>
          <CloseView onPress={() => navigation.goBack()}>
            <Ionicons
              name="ios-close"
              size={36}
              color="#4775f2"
              style={{ marginTop: -2 }}
            />
          </CloseView>
          <Content>
            <Markdown
              body={section.content}
              pureCSS={htmlStyles}
              scalesPageToFit={false}
              scrollEnabled={false}
              onNavigationStateChange={(event) => {
                if (event.url != "about:blank") {
                  Linking.openURL(event.url);
                }
              }}
            />
          </Content>
        </Container>
      </ScrollContainer>
      <StatusBar hidden />
    </>
  );
}
Example #10
Source File: index.js    From be-the-hero with MIT License 5 votes vote down vote up
export default function Detail() {
  const navigation = useNavigation()
  const route = useRoute()

  const incident = route.params.incident
  const message = `Olá ${incident.name}, estou  entrando em contato pois gostaria  de ajudar no caso "${incident.title}" com o valor de "${Intl.NumberFormat('pt-BR', { style: 'currency', currency: 'BRL' }).format(incident.value)}" `

  function navigateBack() {
    navigation.goBack()
  }

  function sendMail() {
    MailComposer.composeAsync({
      subject: `Herói do caso: ${incident.title}`,
      recipients: [incident.email],
      body: message,
    })
  }

  function sendWhatsApp() {
    Linking.openURL(`whatsapp://send?phone=${incident.whatsapp}&text=${message}`)
  }

  return (
    <View style={styles.container}>
      <View style={styles.header}>
        <Image source={logoImg} />
        <TouchableOpacity onPress={navigateBack}>
          <Feather name="arrow-left" size={28} color="#e02041" />
        </TouchableOpacity>
      </View>

      <View style={styles.incident}>

        <Text style={[styles.incidentProperty, { marginTop: 0 }]}> ONG: </Text>
        <Text style={styles.incidentValue}> {incident.name} de {incident.city}/{incident.uf} </Text>

        <Text style={styles.incidentProperty}> CASO: </Text>
        <Text style={styles.incidentValue}> {incident.title} </Text>

        <Text style={styles.incidentProperty}> VALOR: </Text>
        <Text style={styles.incidentValue}> {Intl.NumberFormat('pt-BR', { style: 'currency', currency: 'BRL' }).format(incident.value)} </Text>

      </View>

      <View style={styles.contactBox}>
        <Text style={styles.heroTitle}> Salve o dia! </Text>
        <Text style={styles.heroTitle}> Seja o herói desse caso. </Text>

        <Text style={styles.heroDescription}> Entre em contato: </Text>

        <View style={styles.actions}>
          <TouchableOpacity style={styles.action} onPress={sendWhatsApp}>
            <Text style={styles.actionText}> WhatsApp </Text>
          </TouchableOpacity>
          <TouchableOpacity style={styles.action} onPress={sendMail}>
            <Text style={styles.actionText}> Email </Text>
          </TouchableOpacity>
        </View>
      </View>
    </View>
  )
}
Example #11
Source File: index.js    From be-the-hero with MIT License 5 votes vote down vote up
export default function Detail() {
  const navigation = useNavigation();
  const route = useRoute();
  const { incident } = route.params;
  const message = `Olá ${incident.ong.name}, estou entrando em contato pois gostaria de ajudar no caso "${incident.title}" com o valor de ${incident.valueFormated}.`;

  function sendMail() {
    MailComposer.composeAsync({
      subject: `Herói do caso: ${incident.title}`,
      recipients: [`${incident.ong.email}`],
      body: message,
    });
  }

  function sendWhatsapp() {
    Linking.openURL(`whatsapp://send?phone=+55${incident.ong.whatsapp}&text=${message}`);
  }

  return (
    <Container>
      <Header>
        <Image source={logoImg} />
        <TouchableOpacity onPress={() => navigation.goBack()}>
          <Feather name="arrow-left" size={28} color={colors.redHero} />
        </TouchableOpacity>
      </Header>

      <Incident>
        <GroupRow>
          <View style={{ marginRight: 16, width: '50%' }}>
            <IncidentProperty style={{ marginTop: 0 }}>
              CASO:
            </IncidentProperty>
            <IncidentValue>{incident.title}</IncidentValue>
          </View>

          <View style={{ flex: 1 }} >
            <IncidentProperty style={{ marginTop: 0 }}>
              ONG:
            </IncidentProperty>
            <IncidentValue ellipsizeMode="tail" >
              {incident.ong.name} de {incident.ong.city}/{incident.ong.uf}
            </IncidentValue>
          </View>
        </GroupRow>

        <IncidentProperty>DESCRIÇÃO:</IncidentProperty>
        <IncidentValue>{incident.description}</IncidentValue>

        <IncidentProperty>VALOR:</IncidentProperty>
        <IncidentValue>{incident.valueFormated}</IncidentValue>
      </Incident>

      <ContactBox>
        <HeroTitle>Salve o dia!</HeroTitle>
        <HeroTitle>Seja o herói desse caso.</HeroTitle>

        <HeroDescription>Entre em contato:</HeroDescription>

        <Actions>
          <Action onPress={sendWhatsapp}>
            <ActionText>WhatsApp</ActionText>
          </Action>

          <Action onPress={sendMail}>
            <ActionText>E-mail</ActionText>
          </Action>
        </Actions>
      </ContactBox>
    </Container>
  );
}
Example #12
Source File: index.js    From SemanaOmnistack11 with MIT License 5 votes vote down vote up
export default function Detail() {
  const navigation = useNavigation();
  const route = useRoute();

  const incident = route.params.incident;
  const message = `Olá ${
    incident.name
  }, estou entrando em contato pois gostaria de ajudar no caso "${
    incident.title
  }" com o valor de ${Intl.NumberFormat("pt-BR", {
    style: "currency",
    currency: "BRL"
  }).format(incident.value)}`;

  function navigateBack() {
    navigation.goBack();
  }

  function sendMail() {
    MailComposer.composeAsync({
      subject: `Herói do caso: ${incident.title}`,
      recipients: [incident.email],
      body: message
    });
  }

  function sendWhatsapp() {
    Linking.openURL(
      `whatsapp://send?phone=${incident.whatsapp}&text=${message}`
    );
  }

  return (
    <View style={styles.container}>
      <View style={styles.header}>
        <Image source={logoImg} />

        <TouchableOpacity onPress={navigateBack}>
          <Feather name="arrow-left" size={28} color="#E82041" />
        </TouchableOpacity>
      </View>

      <View style={styles.incident}>
        <Text style={[styles.incidentProperty, { marginTop: 0 }]}>ONG:</Text>
        <Text style={styles.incidentValue}>
          {incident.name} de {incident.city}/{incident.uf}
        </Text>

        <Text style={styles.incidentProperty}>CASO:</Text>
        <Text style={styles.incidentValue}>{incident.title}</Text>

        <Text style={styles.incidentProperty}>VALOR:</Text>
        <Text style={styles.incidentValue}>
          {Intl.NumberFormat("pt-BR", {
            style: "currency",
            currency: "BRL"
          }).format(incident.value)}
        </Text>
      </View>

      <View style={styles.contactBox}>
        <Text style={styles.heroTitle}>Salve o dia!</Text>
        <Text style={styles.heroTitle}>Seja o herói desse caso.</Text>

        <Text style={styles.heroDescription}>Entre em contato:</Text>

        <View style={styles.actions}>
          <TouchableOpacity style={styles.action} onPress={sendWhatsapp}>
            <Text style={styles.actionText}>WhatsApp</Text>
          </TouchableOpacity>

          <TouchableOpacity style={styles.action} onPress={sendMail}>
            <Text style={styles.actionText}>E-mail</Text>
          </TouchableOpacity>
        </View>
      </View>
    </View>
  );
}
Example #13
Source File: Leaderboard.js    From Legacy with Mozilla Public License 2.0 5 votes vote down vote up
UserTile = React.memo(function ({ i, index, week }) {
  var theme = useSelector(i => i.themes[i.theme]);
  var [open, setOpen] = React.useState(false);
  var dark = false;
  var route = useRoute();
  var level_colors = useLevelColours();
  if (theme.dark) {
    dark = true;
  }
  const types = week?.requirements ?? []
  var user = useAPIRequest(open ? {
    endpoint: `weekly/player/v1`,
    data: {
      user_id: i.i,
      week_id: route.params.week
    },
    cuppazee: true
  } : null)
  return <View style={{ padding: 4 }}>
    <Card noPad>
      <TouchableRipple onPress={() => {
        setOpen(!open)
      }}>
        <View style={{ flexDirection: "row", alignItems: "center" }}>
          <View style={{ paddingHorizontal: 8, paddingVertical: 4 }}>
            <Image source={getIcon(`https://munzee.global.ssl.fastly.net/images/avatars/ua${i?.i?.toString?.(36)}.png`)} style={{ width: 36, height: 36, borderRadius: 18 }} />
          </View>
          <View style={{ paddingHorizontal: 8, paddingLeft: 0, flex: 1, flexDirection: "row", alignItems: "center" }}>
            <Text allowFontScaling={false} style={{ fontSize: 16, ...font("bold"), color: theme.page_content.fg }} numberOfLines={1} ellipsizeMode={"tail"}>#{index + 1} - {i.n}</Text>
          </View>
          <View style={{ alignSelf: "stretch", borderTopRightRadius: 8, borderBottomRightRadius: open ? 0 : 8, borderLeftWidth: dark ? 2 : 0, borderLeftColor: dark ? level_colors[Math.max(0, Math.min(Math.ceil(i.p / 50), 5))].bg : undefined, backgroundColor: dark ? undefined : level_colors[Math.max(0, Math.min(Math.ceil(i.p / 50), 5))].bg, width: 60, flexDirection: "row", alignItems: "center", justifyContent: "center" }}>
            <Text allowFontScaling={false} style={{ color: level_colors[Math.max(0, Math.min(Math.ceil(i.p / 50), 5))].fg, fontSize: 16, ...font("bold") }}>{i.p?.toLocaleString?.() || "0"}</Text>
            {week && !!i.f && status(week) === "resultssoon" && <MaterialCommunityIcons name="check-bold" color={theme.page_content.fg} style={{ marginLeft: 4 }} size={16} />}
          </View>
        </View>
      </TouchableRipple>
      <Portal>
        <Dialog
          visible={open}
          onDismiss={() => { setOpen(false) }}
          style={{ maxWidth: 390, alignSelf: "center", borderRadius: 8, backgroundColor: theme.page_content.bg }}>
          <View style={{ flexDirection: "row", alignItems: "center" }}>
            <View style={{ paddingHorizontal: 8, paddingVertical: 4 }}>
              <Image source={getIcon(`https://munzee.global.ssl.fastly.net/images/avatars/ua${i?.i?.toString?.(36)}.png`)} style={{ width: 36, height: 36, borderRadius: 18 }} />
            </View>
            <View style={{ paddingHorizontal: 8, paddingLeft: 0, flex: 1, justifyContent: "center" }}>
              <Text allowFontScaling={false} style={{ fontSize: 16, ...font("bold"), color: theme.page_content.fg }} numberOfLines={1} ellipsizeMode={"tail"}>#{index + 1} - {i.n}</Text>
            </View>
            <View style={{ alignSelf: "stretch", borderTopRightRadius: 8, borderBottomRightRadius: open ? 0 : 8, borderLeftWidth: dark ? 2 : 0, borderLeftColor: dark ? level_colors[Math.max(0, Math.min(Math.ceil(i.p / 50), 5))].bg : undefined, backgroundColor: dark ? undefined : level_colors[Math.max(0, Math.min(Math.ceil(i.p / 50), 5))].bg, width: 60, alignItems: "center", justifyContent: "center" }}>
              <Text allowFontScaling={false} style={{ color: level_colors[Math.max(0, Math.min(Math.ceil(i.p / 50), 5))].fg, fontSize: 16, ...font("bold") }}>{i.p?.toLocaleString?.() || "0"}</Text>
            </View>
          </View>
          <View style={{ flexDirection: "row", alignItems: "center", flexWrap: "wrap" }}>
            {types.map((x, xi) => <View key={x.id} style={{ padding: 4, width: 80, flexGrow: 1, alignItems: "center", opacity: ((user?.d || [])[xi] ?? 0) > 0 ? 1 : 0.4 }}>
              <Image style={{ height: 32, width: 32, marginHorizontal: 8 }} source={getIcon(x.type)} />
              <Text allowFontScaling={false} style={{ ...font("bold"), fontSize: 16, color: theme.page_content.fg }}>{(user?.d || [])[xi] ?? '?'}</Text>
            </View>)}
          </View>
        </Dialog>
      </Portal>
    </Card>
  </View>
})
Example #14
Source File: index.js    From InstagramClone with MIT License 4 votes vote down vote up
StoryScreen = () => {

  const [stories, setStories] = useState([]);
  const [activeStoryIndex, setActiveStoryIndex] = useState(null);

  const route = useRoute();

  useEffect(() => {
    fetchStories();
    setActiveStoryIndex(0);
  }, []);

  const fetchStories = async () => {
    try {
      const storiesData = await API.graphql(graphqlOperation(listStorys));
      console.log(storiesData);
      setStories(storiesData.data.listStorys.items);
    } catch (e) {
      console.log('error fetching stories');
      console.log(e)
    }
  }

  const handleNextStory = () => {
    if (activeStoryIndex >= stories.length - 1) {
      return;
    }
    setActiveStoryIndex(activeStoryIndex + 1);
  }

  const handlePrevStory = () => {
    if (activeStoryIndex <= 0) {
      return;
    }
    setActiveStoryIndex(activeStoryIndex - 1);
  }

  const handlePress = (evt) => {
    const x = evt.nativeEvent.locationX;
    const screenWidth = Dimensions.get('window').width;

    if (x < screenWidth / 2) {
      handlePrevStory();
    } else {
      handleNextStory();
    }
  }

  if (!stories || stories.length === 0) {
    return (
      <SafeAreaView>
        <ActivityIndicator />
      </SafeAreaView>
    )
  }

  const activeStory = stories[activeStoryIndex];

  return (
    <SafeAreaView style={styles.container}>
      <TouchableWithoutFeedback onPress={handlePress}>
        <ImageBackground source={{uri: activeStory.image}} style={styles.image}>
          <View style={styles.userInfo}>
            <ProfilePicture uri={activeStory.user.image} size={50} />
            <Text style={styles.userName}>{activeStory.user.name}</Text>
            <Text style={styles.postedTime}>{activeStory.createdAt}</Text>
          </View>
          <View style={styles.bottomContainer}>
            <View style={styles.cameraButton}>
              <Feather name="camera" size={30} color={'#ffffff'}  />
            </View>
            <View style={styles.textInputContainer}>
              <TextInput
                style={styles.textInput}
                editable
                placeholder="Send message"
                placeholderTextColor={"white"}
              />
            </View>
            <View style={styles.messageButton}>
              <Ionicons name="paper-plane-outline" size={35} color={"#ffffff"}/>
            </View>
          </View>
        </ImageBackground>
      </TouchableWithoutFeedback>
    </SafeAreaView>
  )
}
Example #15
Source File: Page.js    From Legacy with Mozilla Public License 2.0 4 votes vote down vote up
export default function () {
  const [mode, setMode] = useSetting('inventory_group_by','category');
  const [zeros, setZeros] = useSetting('inventory_include_zeros','all');
  var { t } = useTranslation()
  var route = useRoute();
  var theme = useSelector(i => i.themes[i.theme]);
  var username = route.params.username;
  const user_id = useAPIRequest({
    endpoint: 'user',
    data: { username },
    function: i => i?.user_id
  })
  var {data, status} = useAPIRequest(user_id ? {
    endpoint: 'user/inventory',
    data: {},
    user: user_id,
    cuppazee: true,
    function: (x) => InventoryConverter(x?.credits, x?.boosters, x?.history, x?.undeployed, mode, zeros),
    extraData: [mode, zeros]
  } : null, 1);
  if (status) {
    if(status === "loading") {
      return <View style={{ flex: 1, justifyContent: "center", alignItems: "center", backgroundColor: theme.page.bg }}>
        <ActivityIndicator size="large" color={theme.page.fg} />
      </View>
    } else {
      return <View style={{ flex: 1, justifyContent: "center", alignItems: "center", backgroundColor: theme.page.bg }}>
      <MaterialCommunityIcons name="alert" color={theme.page.fg} size={48} />
      <Text allowFontScaling={false} style={{ fontSize: 16, ...font("bold"), textAlign: "center", color: theme.page_content.fg }}>{t('error:' + status)}</Text>
    </View>
    }
  } else if (data === null) {
    return <View style={{ flex: 1, justifyContent: "center", alignItems: "center", backgroundColor: theme.page.bg }}>
    <MaterialCommunityIcons name="alert" color={theme.page.fg} size={48} />
    <Text allowFontScaling={false} style={{ fontSize: 16, ...font("bold"), textAlign: "center", color: theme.page_content.fg }}>{t('error:missing_data.locked')}</Text>
  </View>
  }
  return <View style={{ flex: 1 }}>
    <ScrollView style={{ flex: 1, backgroundColor: theme.page.bg }} contentContainerStyle={{ padding: 4, paddingBottom: 92 }}>
      <View style={{flexDirection:"row",flexWrap:"wrap"}}>
        <View style={{flexGrow: 1, width: 400, maxWidth: "100%", padding: 4}}>
          <Dropdown dense={true} mode="outlined" selectedValue={mode} onValueChange={setMode}>
            {modes.map(i=><DropdownItem label={`Group by ${i.label}`} value={i.value} />)}
          </Dropdown>
        </View>
        <View style={{flexGrow: 1, width: 400, maxWidth: "100%", padding: 4}}>
          <Dropdown enabled={mode!=="type"} dense={true} mode="outlined" selectedValue={zeros} onValueChange={setZeros}>
            <DropdownItem label={`Include Zeros: Yes`} value="all" />
            <DropdownItem label={`Include Zeros: No`} value="none" />
          </Dropdown>
        </View>
      </View>
      <View style={{ flexDirection: "row", flexWrap: "wrap", justifyContent: "center" }}>
        {Object.entries(data?.types || {}).sort(mode === "category" ? (a, b) => (categories.find(i => i.id == b[0])?.priority || 0) - (categories.find(i => i.id == a[0])?.priority || 0) : (a, b) => b[1].length - a[1].length).map(([label, list]) => <View style={{ padding: 4, width: 400, flexGrow: 1, maxWidth: "100%" }}>
          <Card noPad>
            <View style={{ flexDirection: "column", width: "100%", alignItems: "center", paddingLeft: 8, paddingRight: 8, borderRadius: 0 }}>
              <View>
                <Text allowFontScaling={false} style={{ color: theme.page_content.fg, fontSize: 20, ...font("bold") }}>
                  {categories.find(i => i.id == label)?.name ?? label}
                </Text>
              </View>
              <View style={{ flexWrap: "wrap", flexDirection: "row", justifyContent: "center" }}>
                {
                  list?.map(i => <InventoryItem key={`${i.icon}|${i.c ? "c" : (i.b ? "b" : (i.u ? "u" : "z"))}`} i={i} />)
                }
              </View>
            </View>
          </Card>
        </View>)}
      </View>
      <View style={{ flexDirection: "row", flexWrap: "wrap", justifyContent: "center" }}>
        <Text allowFontScaling={false} style={{ color: theme.page_content.fg, fontSize: 24, ...font("bold"), marginLeft: 4 }}>
          {t('inventory:history')}
        </Text>
      </View>
      <View style={{ flexDirection: "row", flexWrap: "wrap", justifyContent: "center" }}>
        {data?.historyBatches.map(i => <ListItem i={i} />)}
      </View>
    </ScrollView>
    <UserFAB username={username} user_id={user_id} />
  </View>
}
Example #16
Source File: SHCPro.js    From Legacy with Mozilla Public License 2.0 4 votes vote down vote up
export default function UserSHCScreen() {
  var moment = useMoment();
  var { t } = useTranslation();
  var theme = useSelector(i => i.themes[i.theme]);
  var date = moment().tz('America/Chicago');
  var dateString = `${date.year()}-${(date.month() + 1).toString().padStart(2, '0')}-${(date.date()).toString().padStart(2, '0')}`
  var theme = useSelector(i => i.themes[i.theme]);
  var dark = false;
  var level_colors = {
    ind: "#ffe97f",
    bot: "#dff77e",
    gro: "#b0fc8d",
    0: "#eb0000",
    1: "#ef6500",
    2: "#fa9102",
    3: "#fcd302",
    4: "#bfe913",
    5: "#55f40b",
    null: "#e3e3e3",
    border: '#000a'
  }
  if (theme.dark) {
    dark = true;
    level_colors.border = "#fffa"
  }
  var route = useRoute();
  if (route.params.date) {
    dateString = route.params.date;
  }
  var username = route.params.username;
  const user_id = useAPIRequest({
    endpoint: 'user',
    data: { username },
    function: i=>i?.user_id
  })
  var categories = [
    { icon: 'rainbowunicorn', name: t('shc:pro.tob'), function: i => i?.bouncer?.type == "tob" },
    { icon: 'nomad', name: t('shc:pro.nomad'), function: i => i?.bouncer?.type == "nomad" },
    { icon: 'retiredunicorn', name: t('shc:pro.retire'), function: i => i?.bouncer?.type == "retiremyth" || i?.bouncer?.type == "zombiepouch" },
    { icon: 'yeti', name: t('shc:pro.myth_1'), function: i => i?.myth_set == "original" },
    { icon: 'cyclops', name: t('shc:pro.myth_2'), function: i => i?.myth_set == "classical" },
    { icon: 'mermaid', name: t('shc:pro.myth_3'), function: i => i?.myth_set == "mirror" },
    { icon: 'poseidon', name: t('shc:pro.myth_4'), function: i => i?.myth_set == "modern" },
    { icon: 'tuli', name: t('shc:pro.pc_1'), function: i => i?.category == "pouch_season_1" },
    { icon: 'magnetus', name: t('shc:pro.pc_2'), function: i => i?.category == "pouch_season_2" },
    { icon: 'oniks', name: t('shc:pro.pc_fun'), function: i => i?.category == "pouch_funfinity" },
    { icon: 'tuxflatrob', name: t('shc:pro.flat'), function: i => i?.bouncer?.type == "flat" },
    { icon: 'morphobutterfly', name: t('shc:pro.temp'), function: i => i?.bouncer?.type == "temppob" },
    { icon: 'scattered', name: t('shc:pro.pscatter'), function: i => i?.scatter && i.state == "physical" },
    { icon: 'feather', name: t('shc:pro.vscatter'), function: i => i?.scatter && i.state == "virtual" },
  ]
  const category_data = useAPIRequest(user_id?{
    endpoint: 'user/activity',
    data: { day: dateString, user_id },
    cuppazee: true,
    function: data=>{
      if(!data) return data;
      if(!data.captures) return null;
      var destinations = data.captures.filter(z => g(z)?.destination?.type == "bouncer")
      var category_data = {};
      for (let category of categories) {
        category_data[category.name] = [];
      }
      for (let x of data.captures) {
        var y = g(x);
        if(!y?.bouncer && !y?.scatter) continue;
        for (let category of categories) {
          if(category.function(y)) {
            category_data[category.name].push({
              i: x,
              m: destinations.find(z => z.captured_at == x.captured_at)
            })
            break;
          };
        }
      }
      return category_data;
    }
  }:null)
  if (!category_data) {
    if(category_data===undefined) {
      return <View style={{flex: 1, justifyContent: "center", alignItems: "center", backgroundColor: theme.page.bg}}>
        <ActivityIndicator size="large" color={theme.page_content.fg} />
      </View>
    } else {
      return <View style={{flex: 1, justifyContent: "center", alignItems: "center", backgroundColor:'#ffaaaa'}}>
        <MaterialCommunityIcons name="alert" size={48} color="#d00" />
      </View>;
    }
  }
  return <View style={{ flex: 1, backgroundColor: theme.page.bg }}>
    <ScrollView style={{ flex: 1 }} contentContainerStyle={{ padding: 8 }}>
      <DateSwitcher dateString={dateString} />
      <View style={{ flexDirection: "row", flexWrap: "wrap", justifyContent: "center" }}>
        {categories.map(i => <View style={{ padding: 4, width: 400, flexGrow: 1, maxWidth: "100%" }}>
          <Card noPad>
            <View style={{ flexDirection: "row", alignItems: "center", flex: 1 }}>
              <View style={{ padding: 8 }}>
                <Image source={getIcon(i?.icon,128)} style={{ width: 36, height: 36 }} />
              </View>
              <View style={{ paddingRight: 8, paddingLeft: 0, flex: 1, justifyContent: "center" }}>
                <Text allowFontScaling={false} style={{ fontSize: 16, ...font("bold"), color: theme.page_content.fg }} numberOfLines={1} ellipsizeMode={"tail"}>{category_data[i.name].length}x {i?.name}</Text>
                <View style={{ flexDirection: "row", alignItems: "center", flexWrap: "wrap" }}>
                  {category_data[i.name].map(x => <SHCItem i={x.i} m={x.m} />)}
                </View>
              </View>
              <View style={{ alignSelf: "stretch", borderTopRightRadius: 8, borderBottomRightRadius: 8, borderLeftWidth: dark ? 2 : 0, borderLeftColor: dark ? level_colors[category_data[i.name].length > 0 ? 5 : 0] : undefined, backgroundColor: dark ? undefined : level_colors[category_data[i.name].length > 0 ? 5 : 0], width: 50, alignItems: "center", justifyContent: "center" }}>
                <Text allowFontScaling={false} style={{ color: theme.page_content.fg, fontSize: 24, ...font("bold") }}>{category_data[i.name].length > 0 ? '✔' : ''}</Text>
              </View>
            </View>
          </Card>
        </View>)}
      </View>
    </ScrollView>

    <UserFAB username={username} user_id={user_id} />
  </View>
}
Example #17
Source File: index.js    From be-the-hero with MIT License 4 votes vote down vote up
export default function Detail() {
  const navigation = useNavigation();
  const route = useRoute();

  const incident = route.params.incident;
  const messege = `Olá ${
    incident.name
  }, estou entrando em contato pois gostaria de ajudar no caso "${
    incident.title
  }" com o valor de ${Intl.NumberFormat('pt-BR', {
    style: 'currency',
    currency: 'BRL',
  }).format(incident.value)}`;

  function navigateBack() {
    navigation.goBack();
  }

  function sendMail() {
    MailComposer.composeAsync({
      subject: `Herói do caso: ${incident.title}`,
      recipients: [incident.email],
      body: messege,
    });
  }

  function sendWhatsapp() {
    Linking.openURL(
      `whatsapp://send?phone=+55${incident.whatsapp}&text=${messege}`
    );
  }

  return (
    <View style={styles.container}>
      <View style={styles.header}>
        <Image source={logoImg} />

        <TouchableOpacity onPress={navigateBack}>
          <Feather name="arrow-left" size={20} color="#E02041" />
        </TouchableOpacity>
      </View>

      <View style={styles.incident}>
        <Text style={[styles.incidentProperty, { marginTop: 0 }]}>ONG:</Text>
        <Text style={styles.incidentValue}>
          {incident.name} de {incident.city}/{incident.uf}
        </Text>

        <Text style={styles.incidentProperty}>CASO:</Text>
        <Text style={styles.incidentValue}>{incident.description}</Text>

        <Text style={styles.incidentProperty}>VALOR:</Text>
        <Text style={styles.incidentValue}>
          {Intl.NumberFormat('pt-BR', {
            style: 'currency',
            currency: 'BRL',
          }).format(incident.value)}
        </Text>
      </View>

      <View style={styles.contactBox}>
        <Text style={styles.heroTitle}>Salve o dia!</Text>
        <Text style={styles.heroTitle}>Seja o herói desse caso.</Text>

        <Text style={styles.heroDescription}>Entre em contato:</Text>

        <View style={styles.actions}>
          <TouchableOpacity style={styles.action} onPress={sendWhatsapp}>
            <FontAwesome name="whatsapp" size={20} color="#fff" />
            <Text style={styles.actionText}>Whatsapp</Text>
          </TouchableOpacity>

          <TouchableOpacity style={styles.action} onPress={sendMail}>
            <Icon name="mail" size={20} color="#fff" />
            <Text style={styles.actionText}>Email</Text>
          </TouchableOpacity>
        </View>
      </View>
    </View>
  );
}
Example #18
Source File: SHCLite.js    From Legacy with Mozilla Public License 2.0 4 votes vote down vote up
export default function UserSHCScreen() {
  var moment = useMoment();
  var { t } = useTranslation();
  var theme = useSelector(i => i.themes[i.theme]);
  var date = moment().tz('America/Chicago');
  var dateString = `${date.year()}-${(date.month() + 1).toString().padStart(2, '0')}-${(date.date()).toString().padStart(2, '0')}`
  var theme = useSelector(i => i.themes[i.theme]);
  var dark = false;
  var level_colors = {
    ind: "#ffe97f",
    bot: "#dff77e",
    gro: "#b0fc8d",
    0: "#eb0000",
    1: "#ef6500",
    2: "#fa9102",
    3: "#fcd302",
    4: "#bfe913",
    5: "#55f40b",
    null: "#e3e3e3",
    border: '#000a'
  }
  if (theme.dark) {
    dark = true;
    level_colors.border = "#fffa"
  }
  var route = useRoute();
  if (route.params.date) {
    dateString = route.params.date;
  }
  var username = route.params.username;
  const user_id = useAPIRequest({
    endpoint: 'user',
    data: { username },
    function: i=>i?.user_id
  })
  var categories = [
    { icon: 'rainbowunicorn', name: t('shc:lite.tob'), function: i => i?.bouncer?.type == "tob" },
    { icon: 'nomad', name: t('shc:lite.nomad'), function: i => i?.bouncer?.type == "nomad" || i?.bouncer?.type == "retiremyth" || i?.bouncer?.type == "zombiepouch" },
    { icon: 'yeti', name: t('shc:lite.myth_1'), function: i => i?.myth_set == "original" || i?.myth_set == "classical" },
    { icon: 'mermaid', name: t('shc:lite.myth_2'), function: i => i?.myth_set == "mirror" || i?.myth_set == "modern" },
    { icon: 'tuli', name: t('shc:lite.pc_1'), function: i => i?.category == "pouch_season_1" },
    { icon: 'oniks', name: t('shc:lite.pc_2'), function: i => i?.category == "pouch_season_2" || i?.category == "pouch_funfinity" },
    { icon: 'tuxflatrob', name: t('shc:lite.flat'), function: i => i?.bouncer?.type == "flat" },
    { icon: 'morphobutterfly', name: t('shc:lite.temp'), function: i => i?.bouncer?.type == "temppob" },
    { icon: 'scattered', name: t('shc:lite.scatter'), function: i => i?.scatter },
  ]
  const category_data = useAPIRequest(user_id?{
    endpoint: 'user/activity',
    data: { day: dateString, user_id },
    cuppazee: true,
    function: data=>{
      if(!data) return data;
      if(!data.captures) return null;
      var destinations = data.captures.filter(z => g(z)?.destination?.type == "bouncer")
      var category_data = {};
      for (let category of categories) {
        category_data[category.name] = [];
      }
      for (let x of data.captures) {
        var y = g(x);
        if(!y?.bouncer && !y?.scatter) continue;
        for (let category of categories) {
          if(category.function(y)) {
            category_data[category.name].push({
              i: x,
              m: destinations.find(z => z.captured_at == x.captured_at)
            })
            break;
          };
        }
      }
      return category_data;
    }
  }:null)
  if (!category_data) {
    if(category_data===undefined) {
      return <View style={{flex: 1, justifyContent: "center", alignItems: "center", backgroundColor: theme.page.bg}}>
        <ActivityIndicator size="large" color={theme.page_content.fg} />
      </View>
    } else {
      return <View style={{flex: 1, justifyContent: "center", alignItems: "center", backgroundColor:'#ffaaaa'}}>
        <MaterialCommunityIcons name="alert" size={48} color="#d00" />
      </View>;
    }
  }
  return <View style={{ flex: 1, backgroundColor: theme.page.bg }}>
    <ScrollView style={{ flex: 1 }} contentContainerStyle={{ padding: 8 }}>
      <DateSwitcher dateString={dateString} />
      <View style={{ flexDirection: "row", flexWrap: "wrap", justifyContent: "center" }}>
        {categories.map(i => <View style={{ padding: 4, width: 400, flexGrow: 1, maxWidth: "100%" }}>
          <Card noPad>
            <View style={{ flexDirection: "row", alignItems: "center", flex: 1 }}>
              <View style={{ padding: 8 }}>
                <Image source={getIcon(i?.icon,128)} style={{ width: 36, height: 36 }} />
              </View>
              <View style={{ paddingRight: 8, paddingLeft: 0, flex: 1, justifyContent: "center" }}>
                <Text allowFontScaling={false} style={{ fontSize: 16, ...font("bold"), color: theme.page_content.fg }} numberOfLines={1} ellipsizeMode={"tail"}>{category_data[i.name].length}x {i?.name}</Text>
                <View style={{ flexDirection: "row", alignItems: "center", flexWrap: "wrap" }}>
                  {category_data[i.name].map(x => <SHCItem i={x.i} m={x.m} />)}
                </View>
              </View>
              <View style={{ alignSelf: "stretch", borderTopRightRadius: 8, borderBottomRightRadius: 8, borderLeftWidth: dark ? 2 : 0, borderLeftColor: dark ? level_colors[category_data[i.name].length > 0 ? 5 : 0] : undefined, backgroundColor: dark ? undefined : level_colors[category_data[i.name].length > 0 ? 5 : 0], width: 50, alignItems: "center", justifyContent: "center" }}>
                <Text allowFontScaling={false} style={{ color: theme.page_content.fg, fontSize: 24, ...font("bold") }}>{category_data[i.name].length > 0 ? '✔' : ''}</Text>
              </View>
            </View>
          </Card>
        </View>)}
      </View>
    </ScrollView>

    <UserFAB username={username} user_id={user_id} />
  </View>
}
Example #19
Source File: POI.js    From Legacy with Mozilla Public License 2.0 4 votes vote down vote up
export default function UserSHCScreen() {
  var moment = useMoment();
  var { t } = useTranslation();
  var theme = useSelector(i => i.themes[i.theme]);
  var date = moment().tz('America/Chicago');
  var dateString = `${date.year()}-${(date.month() + 1).toString().padStart(2, '0')}-${(date.date()).toString().padStart(2, '0')}`
  var theme = useSelector(i => i.themes[i.theme]);
  var dark = false;
  var level_colors = {
    ind: "#ffe97f",
    bot: "#dff77e",
    gro: "#b0fc8d",
    0: "#eb0000",
    1: "#ef6500",
    2: "#fa9102",
    3: "#fcd302",
    4: "#bfe913",
    5: "#55f40b",
    null: "#e3e3e3",
    border: '#000a'
  }
  if (theme.dark) {
    dark = true;
    level_colors.border = "#fffa"
  }
  var route = useRoute();
  if (route.params.date) {
    dateString = route.params.date;
  }
  var username = route.params.username;
  const user_id = useAPIRequest({
    endpoint: 'user',
    data: { username },
    function: i=>i?.user_id
  })
  var categories = types.filter(i=>i.category==="poi").map(i=>({
    icon: i.icon,
    name: i.name.replace('POI ',''),
    function: c => c.icon === i.icon
  }))
  const category_data = useAPIRequest(user_id?{
    endpoint: 'user/activity',
    data: { day: dateString, user_id },
    cuppazee: true,
    function: data=>{
      if(!data) return data;
      if(!data.captures) return null;
      var category_data = {};
      for (let category of categories) {
        category_data[category.name] = [];
      }
      for (let x of data.captures) {
        var y = g(x);
        if(y?.category!=="poi") continue;
        for (let category of categories) {
          if(category.function(y)) {
            category_data[category.name].push({
              i: x
            })
            break;
          };
        }
      }
      return category_data;
    }
  }:null)
  if (!category_data) {
    if(category_data===undefined) {
      return <View style={{flex: 1, justifyContent: "center", alignItems: "center", backgroundColor: theme.page.bg}}>
        <ActivityIndicator size="large" color={theme.page_content.fg} />
      </View>
    } else {
      return <View style={{flex: 1, justifyContent: "center", alignItems: "center", backgroundColor:'#ffaaaa'}}>
        <MaterialCommunityIcons name="alert" size={48} color="#d00" />
      </View>;
    }
  }
  return <View style={{ flex: 1, backgroundColor: theme.page.bg }}>
    <ScrollView style={{ flex: 1 }} contentContainerStyle={{ padding: 8 }}>
      <DateSwitcher dateString={dateString} />
      <View style={{ flexDirection: "row", flexWrap: "wrap", justifyContent: "center" }}>
        {categories.map(i => <View style={{ padding: 4, width: 300, flexGrow: 1, maxWidth: "100%" }}>
          <Card noPad>
            <View style={{ flexDirection: "row", alignItems: "center", flex: 1 }}>
              <View style={{ padding: 8 }}>
                <Image source={getIcon(i?.icon,128)} style={{ width: 36, height: 36 }} />
              </View>
              <View style={{ paddingRight: 8, paddingLeft: 0, flex: 1, justifyContent: "center" }}>
                <Text allowFontScaling={false} style={{ fontSize: 16, ...font("bold"), color: theme.page_content.fg }} numberOfLines={1} ellipsizeMode={"tail"}>{category_data[i.name].length}x {i?.name}</Text>
                <View style={{ flexDirection: "row", alignItems: "center", flexWrap: "wrap" }}>
                  {category_data[i.name].map(x => <SHCItem i={x.i} m={x.m} />)}
                </View>
              </View>
              <View style={{ alignSelf: "stretch", borderTopRightRadius: 8, borderBottomRightRadius: 8, borderLeftWidth: dark ? 2 : 0, borderLeftColor: dark ? level_colors[category_data[i.name].length > 0 ? 5 : 0] : undefined, backgroundColor: dark ? undefined : level_colors[category_data[i.name].length > 0 ? 5 : 0], width: 50, alignItems: "center", justifyContent: "center" }}>
                <Text allowFontScaling={false} style={{ color: theme.page_content.fg, fontSize: 24, ...font("bold") }}>{category_data[i.name].length > 0 ? '✔' : ''}</Text>
              </View>
            </View>
          </Card>
        </View>)}
      </View>
    </ScrollView>

    <UserFAB username={username} user_id={user_id} />
  </View>
}
Example #20
Source File: Colour.js    From Legacy with Mozilla Public License 2.0 4 votes vote down vote up
export default function UserSHCScreen() {
  var moment = useMoment();
  var { t } = useTranslation();
  var theme = useSelector(i => i.themes[i.theme]);
  var date = moment().tz('America/Chicago');
  var dateString = `${date.year()}-${(date.month() + 1).toString().padStart(2, '0')}-${(date.date()).toString().padStart(2, '0')}`
  var theme = useSelector(i => i.themes[i.theme]);
  var dark = false;
  var level_colors = {
    ind: "#ffe97f",
    bot: "#dff77e",
    gro: "#b0fc8d",
    0: "#eb0000",
    1: "#ef6500",
    2: "#fa9102",
    3: "#fcd302",
    4: "#bfe913",
    5: "#55f40b",
    null: "#e3e3e3",
    border: '#000a'
  }
  if (theme.dark) {
    dark = true;
    level_colors.border = "#fffa"
  }
  var route = useRoute();
  if (route.params.date) {
    dateString = route.params.date;
  }
  var username = route.params.username;
  const user_id = useAPIRequest({
    endpoint: 'user',
    data: { username },
    function: i=>i?.user_id
  })
  var categories = types.filter(i=>i.category==="virtual"&&!i.credit).map(i=>({
    icon: i.icon,
    name: i.name.replace('Virtual ',''),
    function: c => c.icon === i.icon
  }))
  const category_data = useAPIRequest(user_id?{
    endpoint: 'user/activity',
    data: { day: dateString, user_id },
    cuppazee: true,
    function: data=>{
      if(!data) return data;
      if(!data.captures) return null;
      var category_data = {};
      for (let category of categories) {
        category_data[category.name] = [];
      }
      for (let x of data.captures) {
        var y = g(x);
        if(y?.category!=="virtual") continue;
        for (let category of categories) {
          if(category.icon===y?.icon) {
            category_data[category.name].push({
              i: x
            })
            break;
          };
        }
      }
      return category_data;
    }
  }:null)
  if (!category_data) {
    if(category_data===undefined) {
      return <View style={{flex: 1, justifyContent: "center", alignItems: "center", backgroundColor: theme.page.bg}}>
        <ActivityIndicator size="large" color={theme.page_content.fg} />
      </View>
    } else {
      return <View style={{flex: 1, justifyContent: "center", alignItems: "center", backgroundColor:'#ffaaaa'}}>
        <MaterialCommunityIcons name="alert" size={48} color="#d00" />
      </View>;
    }
  }
  return <View style={{ flex: 1, backgroundColor: theme.page.bg }}>
    <ScrollView style={{ flex: 1 }} contentContainerStyle={{ padding: 8 }}>
      <DateSwitcher dateString={dateString} />
      <View style={{ flexDirection: "row", flexWrap: "wrap", justifyContent: "center" }}>
        {categories.map(i => <View style={{ padding: 4, width: 100, flexGrow: 1, maxWidth: "100%" }}>
          <Card noPad>
            <View style={{ alignItems: "center" }}>
              <View style={{ paddingTop: 8 }}>
                <Image source={getIcon(i?.icon,128)} style={{ width: 36, height: 36 }} />
              </View>
              <Text allowFontScaling={false} style={{ fontSize: 12, marginBottom: 4, ...font("bold"), textAlign: "center", color: theme.page_content.fg }} numberOfLines={1} ellipsizeMode={"tail"}>{i?.name}</Text>
              <View style={{ height: 24, alignSelf: "stretch", borderBottomLeftRadius: 8, borderBottomRightRadius: 8, borderTopWidth: dark ? 2 : 0, borderTopColor: dark ? level_colors[category_data[i.name].length > 0 ? 5 : 0] : undefined, backgroundColor: dark ? undefined : level_colors[category_data[i.name].length > 0 ? 5 : 0], alignItems: "center", justifyContent: "center" }}>
                <Text allowFontScaling={false} style={{ color: theme.page_content.fg, fontSize: 16, ...font("bold") }}>{category_data[i.name].length||''}</Text>
              </View>
            </View>
          </Card>
        </View>)}
      </View>
    </ScrollView>

    <UserFAB username={username} user_id={user_id} />
  </View>
}
Example #21
Source File: Sidebar.js    From Legacy with Mozilla Public License 2.0 4 votes vote down vote up
export default function UserActivitySidebar({ filters: filterinput, onFiltersChange }) {
  var [filters, setFilters] = React.useState({ activity: new Set(), state: new Set(), category: new Set() });
  React.useEffect(() => {
    setFilters(filterinput)
  }, [filterinput]);
  var moment = useMoment();
  var theme = useSelector(i => i.themes[i.theme]);
  const {t} = useTranslation();
  var date = moment().tz('America/Chicago');
  var dateString = `${date.year()}-${(date.month() + 1).toString().padStart(2, '0')}-${(date.date()).toString().padStart(2, '0')}`
  var route = useRoute();
  if (route.params.date) {
    dateString = route.params.date;
  }
  var username = route.params.username
  var userdata = useAPIRequest({
    endpoint: 'user',
    data: { username }
  })
  let user_id = userdata?.user_id
  var data = useAPIRequest(user_id ? {
    endpoint: 'user/activity',
    data: { day: dateString, user_id },
    cuppazee: true
  } : null)
  var all = data ? [...data.captures, ...data.deploys, ...data.captures_on] : [];
  var allTypes = all.map(i => getType(i.pin));
  var stateOptions = Array.from(new Set(allTypes.map(i => i?.state || "N/A"))).map(i => ({
    title: stateNames[i] ?? i,
    id: i
  }));
  var categoryOptions = Array.from(new Set(allTypes.map(i => i?.category || "N/A"))).map(i => ({
    title: categories.find(c => c.id == i)?.name ?? i,
    id: i
  }));
  var activityOptions = [
    {
      title: "Captures",
      id: "captures"
    },
    {
      title: "Deploys",
      id: "deploys"
    },
    {
      title: "Capons",
      id: "captures_on"
    }
  ]
  return <ScrollView style={{ flex: 1 }}>
    <View style={{ padding: 4 }}>
      <Button icon="check" mode="contained" color={theme.navigation.bg} onPress={() => onFiltersChange?.(filters)}>{t('activity:filters.update')}</Button>
    </View>
    <UserActivityFilterSection
      filter={filters.activity}
      onFilterChange={filter => setFilters({
        ...filters,
        activity: filter
      })}
      title={t('activity:filters.activity')}
      options={activityOptions}
    />
    <UserActivityFilterSection
      filter={filters.state}
      onFilterChange={filter => setFilters({
        ...filters,
        state: filter
      })}
      title={t('activity:filters.state')}
      options={stateOptions}
    />
    <UserActivityFilterSection
      filter={filters.category}
      onFilterChange={filter => setFilters({
        ...filters,
        category: filter
      })}
      title={t('activity:filters.category')}
      options={categoryOptions}
    />
  </ScrollView>
}
Example #22
Source File: Post.js    From reddit-clone with MIT License 4 votes vote down vote up
Post = ({
  index,
  postId,
  userId,
  score,
  type,
  title,
  author,
  category,
  text,
  comments,
  created,
  url,
  votes,
  views,
  setIsLoaading,
  setData,
  postType,
  deleteButton,
  deletePost
}) => {
  const { colors } = useTheme()
  const navigation = useNavigation()
  const { authState } = React.useContext(AuthContext)
  const route = useRoute()

  const isUpVoted = () => {
    return votes.find(v => v.user === userId)?.vote === 1
  }

  const isDownVoted = () => {
    return votes.find(v => v.user === userId)?.vote === -1
  }

  const upVote = async () => {
    setIsLoaading(true)
    const { data } = await axios.get(`post/${postId}/upvote`)
    if (postType !== 'item') {
      setData(prevData => {
        prevData[index] = data
        return prevData
      })
    } else {
      setData(data)
    }
    setIsLoaading(false)
  }

  const downVote = async () => {
    setIsLoaading(true)
    const { data } = await axios.get(`post/${postId}/downvote`)
    if (postType !== 'item') {
      setData(prevData => {
        prevData[index] = data
        return prevData
      })
    } else {
      setData(data)
    }
    setIsLoaading(false)
  }

  const unVote = async () => {
    setIsLoaading(true)
    const { data } = await axios.get(`post/${postId}/unvote`)
    if (postType !== 'item') {
      setData(prevData => {
        prevData[index] = data
        return prevData
      })
    } else {
      setData(data)
    }
    setIsLoaading(false)
  }

  return (
    <View
      as={SafeAreaView}
      style={[
        styles.container,
        { backgroundColor: colors.bgColor, borderColor: colors.postBorder }
      ]}
    >
      <View style={styles.headerContainer}>
        <View style={styles.headerLeft}>
          <Text style={[styles.regularFont, { color: colors.text }]}>{category} </Text>
          <Text
            style={[styles.italicFont, { color: colors.blue }]}
            onPress={() => navigation.navigate('User', { username: author.username })}
          >
            @{author?.username} ·{' '}
          </Text>
          <Text style={[styles.dateText, { color: colors.text }]}>{moment(created).fromNow()}</Text>
        </View>
        <View style={styles.headerRight}>
          {deleteButton && author?.id === authState.userInfo.id && (
            <TouchableOpacity style={styles.trash} activeOpacity={0.5} onPress={deletePost}>
              <Trash color={colors.red} width={20} height={20} />
            </TouchableOpacity>
          )}
        </View>
      </View>
      <Text
        style={[styles.title, { color: colors.text }]}
        onPress={() => navigation.navigate('PostDetail', { postId, category, comments })}
      >
        {title}
      </Text>
      <Text
        numberOfLines={route.name === 'PostDetail' ? 10000 : 10}
        style={[
          styles.regularFont,
          { color: colors.text },
          type === 'link' && route.name === 'PostDetail' && styles.link
        ]}
        onPress={() =>
          route.name === 'PostDetail' && type === 'link'
            ? Linking.openURL(url)
            : navigation.navigate('PostDetail', { postId, category, comments })
        }
      >
        {type === 'link' ? url : text}
      </Text>
      <View style={styles.bottomContainer}>
        <View style={styles.centerAlign}>
          <TouchableOpacity onPress={() => (isUpVoted() ? unVote() : upVote())}>
            <ArrowUp
              width={22}
              height={22}
              strokeWidth={4}
              color={isUpVoted() ? colors.green : colors.icon}
            />
          </TouchableOpacity>
          <Text style={[styles.score, { color: colors.text }]}>{score}</Text>
          <TouchableOpacity onPress={() => (isDownVoted() ? unVote() : downVote())}>
            <ArrowDown
              width={22}
              height={22}
              strokeWidth={4}
              color={isDownVoted() ? colors.red : colors.icon}
            />
          </TouchableOpacity>
        </View>
        <TouchableOpacity
          style={styles.centerAlign}
          activeOpacity={0.7}
          onPress={() => navigation.navigate('PostDetail', { postId, category, comments })}
        >
          <MessageSquare
            color={colors.icon}
            style={styles.commentIcon}
            width={20}
            height={20}
            strokeWidth={3}
          />
          <Text style={[styles.commentText, { color: colors.text }]}>{comments?.length}</Text>
        </TouchableOpacity>
        <Text style={[styles.italicFont, { color: colors.text }]}>{views} views</Text>
      </View>
    </View>
  )
}
Example #23
Source File: Type.js    From Legacy with Mozilla Public License 2.0 4 votes vote down vote up
export default function SettingsScreen() {
  var {t} = useTranslation()
  var moment = useMoment();
  var route = useRoute();
  var munzee_icon = route.params.munzee;
  var munzee = getType(munzee_icon);
  var theme = useSelector(i=>i.themes[i.theme]);
  var nav = useNavigation();
  if(!munzee) return null;
  return (
    <ScrollView style={{ backgroundColor: theme.page_content.bg }} contentContainerStyle={{padding:8}}>
      <View style={{alignItems:"center"}}>
        <Image source={getIcon(munzee.icon)} style={{height:48,width:48}} />
        <Text allowFontScaling={false} style={{color: theme.page_content.fg,fontSize:24,...font("bold")}}>{munzee.name}</Text>
        <Text allowFontScaling={false} style={{color: theme.page_content.fg,fontSize:20,...font("bold")}}>{t('db:type.info',{icon: munzee.icon, id: munzee.id})}</Text>
      </View>
      <View style={{flexDirection:"row",flexWrap:"wrap",justifyContent:"center"}}>
        {munzee.state!="bouncer"&&<CustomChip label={`${u(munzee.state)}`}/>}
        {munzee.card&&<CustomChip label={`${u(munzee.card)} Edition`}/>}
        {munzee.bouncer&&<CustomChip label="Bouncer"/>}
        {munzee.host&&<CustomChip label="Bouncer Host"/>}
        {munzee.elemental&&<CustomChip label="Elemental"/>}
        {munzee.event=="custom"&&<CustomChip label="Custom Event"/>}
        {munzee.unique&&<CustomChip label="Unique"/>}
        {munzee.destination?.max_rooms&&<CustomChip label={`${munzee.destination?.max_rooms} Rooms`}/>}
        <CustomChip onPress={()=>nav.navigate('DBCategory',{category:munzee.category})} label={`Category: ${getCategory(munzee.category)}`}/>
        {munzee.virtual_colors?.map(i=><CustomChip label={`Virtual Color: ${u(i)}`}/>)}
      </View>
      {categories.find(i=>i.id==munzee.category)?.seasonal&&<View style={{alignItems:"center"}}>
        <Text allowFontScaling={false} style={{color:theme.page_content.fg}}>{moment(categories.find(i=>i.id==munzee.category).seasonal.starts).format('L LT')} - {moment(categories.find(i=>i.id==munzee.category).seasonal.ends).format('L LT')}</Text>
        <Text allowFontScaling={false} style={{color:theme.page_content.fg}}>{t('bouncers:duration',{duration:moment.duration(moment(categories.find(i=>i.id==munzee.category).seasonal.starts).diff(moment(categories.find(i=>i.id==munzee.category).seasonal.ends))).humanize()})}</Text>
      </View>}

      {/* Points */}
      {munzee.points&&<>
        <View style={{height:1,backgroundColor:theme.page_content.fg,opacity:0.5,margin:8}}></View>
        <View style={{alignItems:"center"}}>
          <Text allowFontScaling={false} style={{color: theme.page_content.fg,fontSize:24,...font("bold")}}>{t('db:type.points')}</Text>
        </View>
        <View style={{flexDirection: "row", flexWrap: "wrap", justifyContent: "center"}}>
          {munzee.points.deploy!==undefined&&<View style={{alignItems:"center",padding:4,width:100}}>
            <MaterialCommunityIcons name="account" size={32} color={theme.page_content.fg} />
            <Text allowFontScaling={false} numberOfLines={1} style={{color: theme.page_content.fg,lineHeight:16,fontSize:16,...font("bold")}}>{munzee.points.deploy}</Text>
            <Text allowFontScaling={false} style={{color: theme.page_content.fg,fontSize:12,...font()}}>{t('db:type.deploy')}</Text>
          </View>}
          {!munzee.points.type&&<>
            <View style={{alignItems:"center",padding:4,width:100}}>
              <MaterialCommunityIcons name="check" size={32} color={theme.page_content.fg} />
              <Text allowFontScaling={false} numberOfLines={1} style={{color: theme.page_content.fg,lineHeight:16,fontSize:16,...font("bold")}}>{munzee.points.capture}</Text>
              <Text allowFontScaling={false} style={{color: theme.page_content.fg,fontSize:12,...font()}}>{t('db:type.capture')}</Text>
            </View>
            <View style={{alignItems:"center",padding:4,width:100}}>
              <MaterialCommunityIcons name="open-in-app" size={32} color={theme.page_content.fg} />
              <Text allowFontScaling={false} numberOfLines={1} style={{color: theme.page_content.fg,lineHeight:16,fontSize:16,...font("bold")}}>{munzee.points.capon}</Text>
              <Text allowFontScaling={false} style={{color: theme.page_content.fg,fontSize:12,...font()}}>{t('db:type.capon')}</Text>
            </View>
          </>}
          {munzee.points.type=="split"&&<View style={{alignItems:"center",padding:4,width:100}}>
            <MaterialCommunityIcons name="call-split" size={32} color={theme.page_content.fg} />
            <Text allowFontScaling={false} numberOfLines={1} style={{color: theme.page_content.fg,lineHeight:16,fontSize:16,...font("bold")}}>{t('db:type.split_val',munzee.points)}</Text>
            <Text allowFontScaling={false} style={{color: theme.page_content.fg,fontSize:12,...font()}}>{t('db:type.split')}</Text>
          </View>}
        </View>
      </>}

      {/* Evo Stages */}
      {munzee.evolution&&<>
        <View style={{height:1,backgroundColor:theme.page_content.fg,opacity:0.5,margin:8}}></View>
        <View style={{alignItems:"center"}}>
          <Text allowFontScaling={false} style={{color: theme.page_content.fg,fontSize:24,...font("bold")}}>{t('db:type.evo')}</Text>
        </View>
        <View style={{flexDirection:"row",flexWrap:"wrap",justifyContent:"center"}}>
          {types.filter(i=>i.evolution?.base===munzee.evolution.base).sort((a,b)=>a.evolution?.stage-b.evolution?.stage).map(i=><TouchableRipple onPress={()=>nav.push('DBType',{munzee:i.icon})}>
            <View style={{alignItems:"center",padding:4,width:100}}>
              <Image source={getIcon(i.icon)} style={{height:32,width:32}} />
              <Text allowFontScaling={false} numberOfLines={1} ellipsizeMode="tail" style={{color: theme.page_content.fg,fontSize:16,...font("bold")}}>{i.name}</Text>
              <Text allowFontScaling={false} style={{color: theme.page_content.fg,fontSize:16,...font()}}>ID: {i.id}</Text>
            </View>
          </TouchableRipple>)}
        </View>
      </>}

      {/* Pouch Creature Stages */}
      {munzee.bouncer?.base&&<>
        <View style={{height:1,backgroundColor:theme.page_content.fg,opacity:0.5,margin:8}}></View>
        <View style={{alignItems:"center"}}>
          <Text allowFontScaling={false} style={{color: theme.page_content.fg,fontSize:24,...font("bold")}}>{t('db:type.pouch')}</Text>
        </View>
        <View style={{flexDirection:"row",flexWrap:"wrap",justifyContent:"center"}}>
          {types.filter(i=>i.bouncer?.base===munzee.bouncer.base).sort((a,b)=>a.bouncer?.stage-b.bouncer?.stage).map(i=><TouchableRipple onPress={()=>nav.push('DBType',{munzee:i.icon})}>
            <View style={{alignItems:"center",padding:4,width:100}}>
              <Image source={getIcon(i.icon)} style={{height:32,width:32}} />
              <Text allowFontScaling={false} numberOfLines={1} ellipsizeMode="tail" style={{color: theme.page_content.fg,fontSize:16,...font("bold")}}>{i.name}</Text>
              <Text allowFontScaling={false} style={{color: theme.page_content.fg,fontSize:16,...font()}}>ID: {i.id}</Text>
            </View>
          </TouchableRipple>)}
        </View>
      </>}

      {/* Can Host */}
      {munzee.can_host?.filter?.(checkCanHost)?.length>0&&<>
        <View style={{height:1,backgroundColor:theme.page_content.fg,opacity:0.5,margin:8}}></View>
        <View style={{alignItems:"center"}}>
          <Text allowFontScaling={false} style={{color: theme.page_content.fg,fontSize:24,...font("bold")}}>{t('db:type.can_host')}</Text>
        </View>
        <View style={{flexDirection:"row",flexWrap:"wrap",justifyContent:"center"}}>
          {munzee.can_host.filter(checkCanHost).map(i=>types.find(x=>x.id==i)).filter(i=>!i.hidden).map(i=><TouchableRipple onPress={()=>nav.push('DBType',{munzee:i.icon})}>
            <View style={{alignItems:"center",padding:4,width:100}}>
              <Image source={getIcon(i.icon)} style={{height:32,width:32}} />
              <Text allowFontScaling={false} numberOfLines={1} ellipsizeMode="tail" style={{color: theme.page_content.fg,fontSize:16,...font("bold")}}>{i.name}</Text>
              <Text allowFontScaling={false} style={{color: theme.page_content.fg,fontSize:16,...font()}}>ID: {i.id}</Text>
            </View>
          </TouchableRipple>)}
        </View>
      </>}

      {/* Lands On */}
      {munzee?.bouncer?.lands_on&&<>
        <View style={{height:1,backgroundColor:theme.page_content.fg,opacity:0.5,margin:8}}></View>
        <View style={{alignItems:"center"}}>
          <Text allowFontScaling={false} style={{color: theme.page_content.fg,fontSize:24,...font("bold")}}>{t('db:type.lands_on')}</Text>
        </View>
        <View style={{flexDirection:"row",flexWrap:"wrap",justifyContent:"center"}}>
          {munzee.bouncer.lands_on.map(i=>types.find(x=>x.id==i)).filter(i=>!i.hidden).map(i=><TouchableRipple onPress={()=>nav.push('DBType',{munzee:i.icon})}>
            <View style={{alignItems:"center",padding:4,width:100}}>
              <Image source={getIcon(i.icon)} style={{height:32,width:32}} />
              <Text allowFontScaling={false} numberOfLines={1} ellipsizeMode="tail" style={{color: theme.page_content.fg,fontSize:16,...font("bold")}}>{i.name}</Text>
              <Text allowFontScaling={false} style={{color: theme.page_content.fg,fontSize:16,...font()}}>ID: {i.id}</Text>
            </View>
          </TouchableRipple>)}
        </View>
      </>}

      {/* Host Types */}
      {types.filter(i=>i.host&&i.host.hosts&&i.host.hosts.includes(munzee.id)).length>0&&<>
        <View style={{height:1,backgroundColor:theme.page_content.fg,opacity:0.5,margin:8}}></View>
        <View style={{alignItems:"center"}}>
          <Text allowFontScaling={false} style={{color: theme.page_content.fg,fontSize:24,...font("bold")}}>{t('db:type.host_types')}</Text>
        </View>
        <View style={{flexDirection:"row",flexWrap:"wrap",justifyContent:"center"}}>
          {types.filter(i=>i.host&&i.host.hosts&&i.host.hosts.includes(munzee.id)).filter(i=>!i.hidden).map(i=><TouchableRipple onPress={()=>nav.push('DBType',{munzee:i.icon})}>
            <View style={{alignItems:"center",padding:4,width:100}}>
              <Image source={getIcon(i.icon)} style={{height:32,width:32}} />
              <Text allowFontScaling={false} numberOfLines={1} ellipsizeMode="tail" style={{color: theme.page_content.fg,fontSize:16,...font("bold")}}>{i.name}</Text>
              <Text allowFontScaling={false} style={{color: theme.page_content.fg,fontSize:16,...font()}}>ID: {i.id}</Text>
            </View>
          </TouchableRipple>)}
        </View>
      </>}

      {/* Hosts */}
      {munzee?.host?.hosts&&<>
        <View style={{height:1,backgroundColor:theme.page_content.fg,opacity:0.5,margin:8}}></View>
        <View style={{alignItems:"center"}}>
          <Text allowFontScaling={false} style={{color: theme.page_content.fg,fontSize:24,...font("bold")}}>{t('db:type.hosts')}</Text>
        </View>
        <View style={{flexDirection:"row",flexWrap:"wrap",justifyContent:"center"}}>
          {munzee.host.hosts.map(i=>types.find(x=>x.id==i)).filter(i=>!i.hidden).map(i=><TouchableRipple onPress={()=>nav.push('DBType',{munzee:i.icon})}>
            <View style={{alignItems:"center",padding:4,width:100}}>
              <Image source={getIcon(i.icon)} style={{height:32,width:32}} />
              <Text allowFontScaling={false} numberOfLines={1} ellipsizeMode="tail" style={{color: theme.page_content.fg,fontSize:16,...font("bold")}}>{i.name}</Text>
              <Text allowFontScaling={false} style={{color: theme.page_content.fg,fontSize:16,...font()}}>ID: {i.id}</Text>
            </View>
          </TouchableRipple>)}
        </View>
      </>}

      {/* Possible Types */}
      {munzee?.host?.hosts&&possibleTypes(munzee?.host?.hosts)&&<>
        <View style={{height:1,backgroundColor:theme.page_content.fg,opacity:0.5,margin:8}}></View>
        <View style={{alignItems:"center"}}>
          <Text allowFontScaling={false} style={{color: theme.page_content.fg,fontSize:24,...font("bold")}}>{t('db:type.possible_types')}</Text>
        </View>
        <View style={{flexDirection:"row",flexWrap:"wrap",justifyContent:"center"}}>
          {possibleTypes(munzee?.host?.hosts).map(i=>types.find(x=>x.id==i)).filter(i=>!i.hidden&&i.state==munzee?.state).map(i=><TouchableRipple onPress={()=>nav.push('DBType',{munzee:i.icon})}>
            <View style={{alignItems:"center",padding:4,width:100}}>
              <Image source={getIcon(i.icon)} style={{height:32,width:32}} />
              <Text allowFontScaling={false} numberOfLines={1} ellipsizeMode="tail" style={{color: theme.page_content.fg,fontSize:16,...font("bold")}}>{i.name}</Text>
              <Text allowFontScaling={false} style={{color: theme.page_content.fg,fontSize:16,...font()}}>ID: {i.id}</Text>
            </View>
          </TouchableRipple>)}
        </View>
      </>}

      {/* Possible Hosts */}
      {munzee?.can_host&&possibleHosts(munzee?.can_host)&&<>
        <View style={{height:1,backgroundColor:theme.page_content.fg,opacity:0.5,margin:8}}></View>
        <View style={{alignItems:"center"}}>
          <Text allowFontScaling={false} style={{color: theme.page_content.fg,fontSize:24,...font("bold")}}>{t('db:type.possible_hosts')}</Text>
        </View>
        <View style={{flexDirection:"row",flexWrap:"wrap",justifyContent:"center"}}>
          {possibleHosts(munzee.can_host).map(i=>types.find(x=>x.id==i)).filter(i=>!i.hidden&&i.state==munzee?.state).map(i=><TouchableRipple onPress={()=>nav.push('DBType',{munzee:i.icon})}>
            <View style={{alignItems:"center",padding:4,width:100}}>
              <Image source={getIcon(i.icon)} style={{height:32,width:32}} />
              <Text allowFontScaling={false} numberOfLines={1} ellipsizeMode="tail" style={{color: theme.page_content.fg,fontSize:16,...font("bold")}}>{i.name}</Text>
              <Text allowFontScaling={false} style={{color: theme.page_content.fg,fontSize:16,...font()}}>ID: {i.id}</Text>
            </View>
          </TouchableRipple>)}
        </View>
      </>}
    </ScrollView>
  );
}
Example #24
Source File: NotesScreen.js    From discovery-mobile-ui with MIT License 4 votes vote down vote up
NotesScreen = ({
  resource,
  createRecordNoteAction,
  editRecordNoteAction,
  collection,
  createCollectionNoteAction,
  editCollectionNoteAction,
}) => {
  const navigation = useNavigation();
  const route = useRoute();
  const editingNote = route?.params?.editingNote;
  const [text, onChangeText] = useState('');
  const [editNoteId, setEditNoteId] = useState(null);
  const [showNoteInput, setShowNoteInput] = useState(false);
  const isResourceNotes = !!resource;

  const closeInput = () => {
    onChangeText('');
    setEditNoteId(null);
    setShowNoteInput(false);
  };

  const discardInputAlert = () => {
    Alert.alert(
      'Discard Edits',
      'Are you sure you want to discard edits to this note?',
      [
        {
          text: 'Cancel',
          onPress: () => {},
          style: 'cancel',
        },
        {
          text: 'Discard',
          onPress: () => closeInput(),
          style: 'destructive',
        },
      ],
    );
  };

  const handleCloseInput = ({ alert }) => {
    if (alert) {
      discardInputAlert();
    } else {
      closeInput();
    }
  };

  const handleSave = () => {
    if (isResourceNotes) {
      if (editNoteId) {
        editRecordNoteAction(resource.id, text, editNoteId);
      } else {
        createRecordNoteAction(resource.id, text);
      }
    } else if (editNoteId) {
      editCollectionNoteAction(editNoteId, text);
    } else {
      createCollectionNoteAction(text);
    }
    closeInput();
  };

  const handleCreateNote = () => {
    setShowNoteInput(true);
  };

  const handleEditNote = (noteId, noteText) => {
    setEditNoteId(noteId);
    onChangeText(noteText);
    setShowNoteInput(true);
  };

  useEffect(() => {
    if (editingNote) {
      handleEditNote(editingNote.id, editingNote.text);
    } else {
      handleCreateNote();
    }
  }, []);

  const hasTextValue = text.length > 0;
  const saveButtonTextStyle = hasTextValue ? styles.saveButtonText : styles.disabledSaveButtonText;
  const noteCount = isResourceNotes
    ? collection.records[resource.id]?.notes && Object.keys(collection.records[resource?.id]?.notes).length // eslint-disable-line max-len
    : Object.keys(collection.notes).length;

  return (
    <SafeAreaView style={styles.root}>
      <Header style={styles.header}>
        <Left>
          <TouchableOpacity onPress={() => navigation.goBack()}>
            <Entypo name="chevron-thin-left" size={20} color="black" />
          </TouchableOpacity>
        </Left>
        <View style={styles.headerTitleContainer}>
          {noteCount > 0 && <HeaderCountIcon count={noteCount} outline />}
          <Title style={styles.headerText}><Text>Notes</Text></Title>
        </View>
        <Right>
          {!showNoteInput && (
            <TouchableOpacity onPress={handleCreateNote} disabled={showNoteInput}>
              <Feather name="plus-square" size={24} color="black" />
            </TouchableOpacity>
          )}
        </Right>
      </Header>
      <ScrollView>
        {isResourceNotes && (
          <View style={styles.resourceCardContainer}>
            <ResourceCard
              resourceId={resource.id}
              resource={resource}
              handleEditNote={handleEditNote}
              editNoteId={editNoteId}
              fromNotesScreen
            />
          </View>
        )}
        {!isResourceNotes && (
          <>
            <View style={styles.collectionHeaderContainer}>
              <View style={styles.collectionLabelContainer}>
                <Text>{collection.label}</Text>
              </View>
            </View>
            <CollectionNotes
              editNoteId={editNoteId}
              handleEditNote={handleEditNote}
              fromNotesScreen
            />
          </>
        )}
      </ScrollView>
      {showNoteInput && (
      <KeyboardAvoidingView behavior="padding">
        <View style={styles.noteEditingActions}>
          <TouchableOpacity onPress={() => handleCloseInput({ alert: true })}>
            <Ionicons name="ios-close-outline" size={24} color="black" />
          </TouchableOpacity>
          <TouchableOpacity style={styles.saveButton} onPress={handleSave} disabled={!hasTextValue}>
            <BaseText variant="title" style={saveButtonTextStyle}>Save</BaseText>
          </TouchableOpacity>
        </View>
        <View style={styles.textInputContainer}>
          <TextInput
            style={styles.textInput}
            onChangeText={onChangeText}
            multiline
            value={text}
            autoFocus
          />
        </View>
      </KeyboardAvoidingView>
      )}
    </SafeAreaView>
  );
}